2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
6 % X X W W IIIII N N DDDD OOO W W %
7 % X X W W I NN N D D O O W W %
8 % X W W I N N N D D O O W W %
9 % X X W W W I N NN D D O O W W W %
10 % X X W W IIIII N N DDDD OOO W W %
13 % MagickCore X11 Utility Methods %
20 % Copyright 1999-2012 ImageMagick Studio LLC, a non-profit organization %
21 % dedicated to making software imaging solutions freely available. %
23 % You may not use this file except in compliance with the License. You may %
24 % obtain a copy of the License at %
26 % http://www.imagemagick.org/script/license.php %
28 % Unless required by applicable law or agreed to in writing, software %
29 % distributed under the License is distributed on an "AS IS" BASIS, %
30 % WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. %
31 % See the License for the specific language governing permissions and %
32 % limitations under the License. %
34 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
42 #include "MagickCore/studio.h"
43 #include "MagickCore/animate.h"
44 #include "MagickCore/artifact.h"
45 #include "MagickCore/blob.h"
46 #include "MagickCore/cache.h"
47 #include "MagickCore/client.h"
48 #include "MagickCore/color.h"
49 #include "MagickCore/color-private.h"
50 #include "MagickCore/colormap.h"
51 #include "MagickCore/composite.h"
52 #include "MagickCore/constitute.h"
53 #include "MagickCore/display.h"
54 #include "MagickCore/distort.h"
55 #include "MagickCore/exception.h"
56 #include "MagickCore/exception-private.h"
57 #include "MagickCore/geometry.h"
58 #include "MagickCore/identify.h"
59 #include "MagickCore/image.h"
60 #include "MagickCore/image-private.h"
61 #include "MagickCore/list.h"
62 #include "MagickCore/locale_.h"
63 #include "MagickCore/log.h"
64 #include "MagickCore/magick.h"
65 #include "MagickCore/memory_.h"
66 #include "MagickCore/monitor.h"
67 #include "MagickCore/nt-base-private.h"
68 #include "MagickCore/option.h"
69 #include "MagickCore/pixel-accessor.h"
70 #include "MagickCore/PreRvIcccm.h"
71 #include "MagickCore/quantize.h"
72 #include "MagickCore/quantum.h"
73 #include "MagickCore/quantum-private.h"
74 #include "MagickCore/resource_.h"
75 #include "MagickCore/resize.h"
76 #include "MagickCore/statistic.h"
77 #include "MagickCore/string_.h"
78 #include "MagickCore/string-private.h"
79 #include "MagickCore/transform.h"
80 #include "MagickCore/utility.h"
81 #include "MagickCore/utility-private.h"
82 #include "MagickCore/widget.h"
83 #include "MagickCore/widget-private.h"
84 #include "MagickCore/xwindow.h"
85 #include "MagickCore/xwindow-private.h"
86 #include "MagickCore/version.h"
90 #if defined(MAGICKCORE_X11_DELEGATE)
91 #include <X11/Xproto.h>
92 #include <X11/Xlocale.h>
93 #if defined(MAGICK_HAVE_POLL)
94 # include <sys/poll.h>
96 #if defined(MAGICKCORE_HAVE_SHARED_MEMORY)
97 #if defined(MAGICKCORE_HAVE_MACHINE_PARAM_H)
98 # include <machine/param.h>
102 #include <X11/extensions/XShm.h>
104 #if defined(MAGICKCORE_HAVE_SHAPE)
105 #include <X11/extensions/shape.h>
111 #define XBlueGamma(color) ClampToQuantum(blue_gamma == 1.0 ? (double) \
112 (color) : ((pow(((double) QuantumScale*(color)),1.0/(double) blue_gamma)* \
114 #define XGammaPacket(map,color) (size_t) (map->base_pixel+ \
115 ((ScaleQuantumToShort(XRedGamma((color)->red))*map->red_max/65535L)* \
117 ((ScaleQuantumToShort(XGreenGamma((color)->green))*map->green_max/65535L)* \
119 ((ScaleQuantumToShort(XBlueGamma((color)->blue))*map->blue_max/65535L)* \
121 #define XGammaPixel(image,map,color) (size_t) (map->base_pixel+ \
122 ((ScaleQuantumToShort(XRedGamma(GetPixelRed(image,color)))*map->red_max/65535L)* \
124 ((ScaleQuantumToShort(XGreenGamma(GetPixelGreen(image,color)))*map->green_max/65535L)* \
126 ((ScaleQuantumToShort(XBlueGamma(GetPixelBlue(image,color)))*map->blue_max/65535L)* \
128 #define XGreenGamma(color) ClampToQuantum(green_gamma == 1.0 ? (double) \
129 (color) : ((pow(((double) QuantumScale*(color)),1.0/(double) green_gamma)* \
131 #define XRedGamma(color) ClampToQuantum(red_gamma == 1.0 ? (double) \
132 (color) : ((pow(((double) QuantumScale*(color)),1.0/(double) red_gamma)* \
134 #define XStandardPixel(map,color) (size_t) (map->base_pixel+ \
135 (((color)->red*map->red_max/65535L)*map->red_mult)+ \
136 (((color)->green*map->green_max/65535L)*map->green_mult)+ \
137 (((color)->blue*map->blue_max/65535L)*map->blue_mult))
139 #define AccentuateModulate ScaleCharToQuantum(80)
140 #define HighlightModulate ScaleCharToQuantum(125)
141 #define ShadowModulate ScaleCharToQuantum(135)
142 #define DepthModulate ScaleCharToQuantum(185)
143 #define TroughModulate ScaleCharToQuantum(110)
145 #define XLIB_ILLEGAL_ACCESS 1
147 #undef NorthWestGravity
149 #undef NorthEastGravity
153 #undef SouthWestGravity
155 #undef SouthEastGravity
162 #define XFD_SET fd_set
166 Enumeration declarations.
180 Typedef declarations.
182 typedef struct _DiversityPacket
197 Constant declaractions.
199 static MagickBooleanType
200 xerror_alert = MagickFalse;
206 *XVisualClassName(const int);
208 static MagickRealType
213 static MagickBooleanType
214 XMakePixmap(Display *,const XResourceInfo *,XWindowInfo *);
217 XMakeImageLSBFirst(const XResourceInfo *,const XWindowInfo *,Image *,
218 XImage *,XImage *,ExceptionInfo *),
219 XMakeImageMSBFirst(const XResourceInfo *,const XWindowInfo *,Image *,
220 XImage *,XImage *,ExceptionInfo *);
223 XSelectWindow(Display *,RectangleInfo *);
226 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
230 % D e s t r o y X R e s o u r c e s %
234 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
236 % DestroyXResources() destroys any X resources.
238 % The format of the DestroyXResources method is:
240 % void DestroyXResources()
242 % A description of each parameter follows:
245 MagickExport void DestroyXResources(void)
254 *magick_windows[MaxXWindows];
260 windows=XSetWindows((XWindows *) ~0);
261 if ((windows == (XWindows *) NULL) || (windows->display == (Display *) NULL))
264 magick_windows[number_windows++]=(&windows->context);
265 magick_windows[number_windows++]=(&windows->group_leader);
266 magick_windows[number_windows++]=(&windows->backdrop);
267 magick_windows[number_windows++]=(&windows->icon);
268 magick_windows[number_windows++]=(&windows->image);
269 magick_windows[number_windows++]=(&windows->info);
270 magick_windows[number_windows++]=(&windows->magnify);
271 magick_windows[number_windows++]=(&windows->pan);
272 magick_windows[number_windows++]=(&windows->command);
273 magick_windows[number_windows++]=(&windows->widget);
274 magick_windows[number_windows++]=(&windows->popup);
275 magick_windows[number_windows++]=(&windows->context);
276 for (i=0; i < (int) number_windows; i++)
278 if (magick_windows[i]->mapped != MagickFalse)
280 (void) XWithdrawWindow(windows->display,magick_windows[i]->id,
281 magick_windows[i]->screen);
282 magick_windows[i]->mapped=MagickFalse;
284 if (magick_windows[i]->name != (char *) NULL)
285 magick_windows[i]->name=(char *)
286 RelinquishMagickMemory(magick_windows[i]->name);
287 if (magick_windows[i]->icon_name != (char *) NULL)
288 magick_windows[i]->icon_name=(char *)
289 RelinquishMagickMemory(magick_windows[i]->icon_name);
290 if (magick_windows[i]->cursor != (Cursor) NULL)
292 (void) XFreeCursor(windows->display,magick_windows[i]->cursor);
293 magick_windows[i]->cursor=(Cursor) NULL;
295 if (magick_windows[i]->busy_cursor != (Cursor) NULL)
297 (void) XFreeCursor(windows->display,magick_windows[i]->busy_cursor);
298 magick_windows[i]->busy_cursor=(Cursor) NULL;
300 if (magick_windows[i]->highlight_stipple != (Pixmap) NULL)
302 (void) XFreePixmap(windows->display,
303 magick_windows[i]->highlight_stipple);
304 magick_windows[i]->highlight_stipple=(Pixmap) NULL;
306 if (magick_windows[i]->shadow_stipple != (Pixmap) NULL)
308 (void) XFreePixmap(windows->display,magick_windows[i]->shadow_stipple);
309 magick_windows[i]->shadow_stipple=(Pixmap) NULL;
311 if (magick_windows[i]->ximage != (XImage *) NULL)
313 XDestroyImage(magick_windows[i]->ximage);
314 magick_windows[i]->ximage=(XImage *) NULL;
316 if (magick_windows[i]->pixmap != (Pixmap) NULL)
318 (void) XFreePixmap(windows->display,magick_windows[i]->pixmap);
319 magick_windows[i]->pixmap=(Pixmap) NULL;
321 if (magick_windows[i]->id != (Window) NULL)
323 (void) XDestroyWindow(windows->display,magick_windows[i]->id);
324 magick_windows[i]->id=(Window) NULL;
326 if (magick_windows[i]->destroy != MagickFalse)
328 if (magick_windows[i]->image != (Image *) NULL)
330 magick_windows[i]->image=DestroyImage(magick_windows[i]->image);
331 magick_windows[i]->image=NewImageList();
333 if (magick_windows[i]->matte_pixmap != (Pixmap) NULL)
335 (void) XFreePixmap(windows->display,
336 magick_windows[i]->matte_pixmap);
337 magick_windows[i]->matte_pixmap=(Pixmap) NULL;
340 if (magick_windows[i]->segment_info != (void *) NULL)
342 #if defined(MAGICKCORE_HAVE_SHARED_MEMORY)
346 segment_info=(XShmSegmentInfo *) magick_windows[i]->segment_info;
347 if (segment_info != (XShmSegmentInfo *) NULL)
348 if (segment_info[0].shmid >= 0)
350 if (segment_info[0].shmaddr != NULL)
351 (void) shmdt(segment_info[0].shmaddr);
352 (void) shmctl(segment_info[0].shmid,IPC_RMID,0);
353 segment_info[0].shmaddr=NULL;
354 segment_info[0].shmid=(-1);
357 magick_windows[i]->segment_info=(void *)
358 RelinquishMagickMemory(magick_windows[i]->segment_info);
361 windows->icon_resources=(XResourceInfo *)
362 RelinquishMagickMemory(windows->icon_resources);
363 if (windows->icon_pixel != (XPixelInfo *) NULL)
365 if (windows->icon_pixel->pixels != (unsigned long *) NULL)
366 windows->icon_pixel->pixels=(unsigned long *)
367 RelinquishMagickMemory(windows->icon_pixel->pixels);
368 if (windows->icon_pixel->annotate_context != (GC) NULL)
369 XFreeGC(windows->display,windows->icon_pixel->annotate_context);
370 windows->icon_pixel=(XPixelInfo *)
371 RelinquishMagickMemory(windows->icon_pixel);
373 if (windows->pixel_info != (XPixelInfo *) NULL)
375 if (windows->pixel_info->pixels != (unsigned long *) NULL)
376 windows->pixel_info->pixels=(unsigned long *)
377 RelinquishMagickMemory(windows->pixel_info->pixels);
378 if (windows->pixel_info->annotate_context != (GC) NULL)
379 XFreeGC(windows->display,windows->pixel_info->annotate_context);
380 if (windows->pixel_info->widget_context != (GC) NULL)
381 XFreeGC(windows->display,windows->pixel_info->widget_context);
382 if (windows->pixel_info->highlight_context != (GC) NULL)
383 XFreeGC(windows->display,windows->pixel_info->highlight_context);
384 windows->pixel_info=(XPixelInfo *)
385 RelinquishMagickMemory(windows->pixel_info);
387 if (windows->font_info != (XFontStruct *) NULL)
389 XFreeFont(windows->display,windows->font_info);
390 windows->font_info=(XFontStruct *) NULL;
392 if (windows->class_hints != (XClassHint *) NULL)
394 if (windows->class_hints->res_name != (char *) NULL)
395 windows->class_hints->res_name=DestroyString(
396 windows->class_hints->res_name);
397 if (windows->class_hints->res_class != (char *) NULL)
398 windows->class_hints->res_class=DestroyString(
399 windows->class_hints->res_class);
400 XFree(windows->class_hints);
401 windows->class_hints=(XClassHint *) NULL;
403 if (windows->manager_hints != (XWMHints *) NULL)
405 XFree(windows->manager_hints);
406 windows->manager_hints=(XWMHints *) NULL;
408 if (windows->map_info != (XStandardColormap *) NULL)
410 XFree(windows->map_info);
411 windows->map_info=(XStandardColormap *) NULL;
413 if (windows->icon_map != (XStandardColormap *) NULL)
415 XFree(windows->icon_map);
416 windows->icon_map=(XStandardColormap *) NULL;
418 if (windows->visual_info != (XVisualInfo *) NULL)
420 XFree(windows->visual_info);
421 windows->visual_info=(XVisualInfo *) NULL;
423 if (windows->icon_visual != (XVisualInfo *) NULL)
425 XFree(windows->icon_visual);
426 windows->icon_visual=(XVisualInfo *) NULL;
428 (void) XSetWindows((XWindows *) NULL);
432 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
436 % X A n n o t a t e I m a g e %
440 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
442 % XAnnotateImage() annotates the image with text.
444 % The format of the XAnnotateImage method is:
446 % MagickBooleanType XAnnotateImage(Display *display,
447 % const XPixelInfo *pixel,XAnnotateInfo *annotate_info,Image *image,
448 % ExceptionInfo *exception)
450 % A description of each parameter follows:
452 % o display: Specifies a connection to an X server; returned from
455 % o pixel: Specifies a pointer to a XPixelInfo structure.
457 % o annotate_info: Specifies a pointer to a XAnnotateInfo structure.
459 % o image: the image.
461 % o exception: return any errors or warnings in this structure.
464 MagickPrivate MagickBooleanType XAnnotateImage(Display *display,
465 const XPixelInfo *pixel,XAnnotateInfo *annotate_info,Image *image,
466 ExceptionInfo *exception)
488 virtual_pixel[CompositePixelChannel];
505 Initialize annotated image.
507 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
508 assert(display != (Display *) NULL);
509 assert(pixel != (XPixelInfo *) NULL);
510 assert(annotate_info != (XAnnotateInfo *) NULL);
511 assert(image != (Image *) NULL);
513 Initialize annotated pixmap.
515 root_window=XRootWindow(display,XDefaultScreen(display));
516 depth=(unsigned int) XDefaultDepth(display,XDefaultScreen(display));
517 annotate_pixmap=XCreatePixmap(display,root_window,annotate_info->width,
518 annotate_info->height,depth);
519 if (annotate_pixmap == (Pixmap) NULL)
522 Initialize graphics info.
524 context_values.background=0;
525 context_values.foreground=(size_t) (~0);
526 context_values.font=annotate_info->font_info->fid;
527 annotate_context=XCreateGC(display,root_window,(unsigned long)
528 (GCBackground | GCFont | GCForeground),&context_values);
529 if (annotate_context == (GC) NULL)
534 (void) XDrawImageString(display,annotate_pixmap,annotate_context,0,
535 (int) annotate_info->font_info->ascent,annotate_info->text,
536 (int) strlen(annotate_info->text));
537 (void) XFreeGC(display,annotate_context);
539 Initialize annotated X image.
541 annotate_ximage=XGetImage(display,annotate_pixmap,0,0,annotate_info->width,
542 annotate_info->height,AllPlanes,ZPixmap);
543 if (annotate_ximage == (XImage *) NULL)
545 (void) XFreePixmap(display,annotate_pixmap);
547 Initialize annotated image.
549 annotate_image=AcquireImage((ImageInfo *) NULL,exception);
550 if (annotate_image == (Image *) NULL)
552 annotate_image->columns=annotate_info->width;
553 annotate_image->rows=annotate_info->height;
555 Transfer annotated X image to image.
557 width=(unsigned int) image->columns;
558 height=(unsigned int) image->rows;
561 (void) XParseGeometry(annotate_info->geometry,&x,&y,&width,&height);
562 (void) GetOneVirtualPixel(image,(ssize_t) x,(ssize_t) y,virtual_pixel,
564 annotate_image->background_color.red=(double)
565 virtual_pixel[RedPixelChannel];
566 annotate_image->background_color.green=(double)
567 virtual_pixel[GreenPixelChannel];
568 annotate_image->background_color.blue=(double)
569 virtual_pixel[BluePixelChannel];
570 annotate_image->background_color.alpha=(double)
571 virtual_pixel[AlphaPixelChannel];
572 if (annotate_info->stencil == ForegroundStencil)
573 annotate_image->matte=MagickTrue;
574 annotate_view=AcquireCacheView(annotate_image);
575 for (y=0; y < (int) annotate_image->rows; y++)
583 q=GetCacheViewAuthenticPixels(annotate_view,0,(ssize_t) y,
584 annotate_image->columns,1,exception);
585 if (q == (Quantum *) NULL)
587 for (x=0; x < (int) annotate_image->columns; x++)
589 SetPixelAlpha(annotate_image,OpaqueAlpha,q);
590 if (XGetPixel(annotate_ximage,x,y) == 0)
593 Set this pixel to the background color.
595 SetPixelRed(annotate_image,ScaleShortToQuantum(
596 pixel->box_color.red),q);
597 SetPixelGreen(annotate_image,ScaleShortToQuantum(
598 pixel->box_color.green),q);
599 SetPixelBlue(annotate_image,ScaleShortToQuantum(
600 pixel->box_color.blue),q);
601 if ((annotate_info->stencil == ForegroundStencil) ||
602 (annotate_info->stencil == OpaqueStencil))
603 SetPixelAlpha(annotate_image,TransparentAlpha,q);
608 Set this pixel to the pen color.
610 SetPixelRed(annotate_image,ScaleShortToQuantum(
611 pixel->pen_color.red),q);
612 SetPixelGreen(annotate_image,ScaleShortToQuantum(
613 pixel->pen_color.green),q);
614 SetPixelBlue(annotate_image,ScaleShortToQuantum(
615 pixel->pen_color.blue),q);
616 if (annotate_info->stencil == BackgroundStencil)
617 SetPixelAlpha(annotate_image,TransparentAlpha,q);
619 q+=GetPixelChannels(annotate_image);
621 if (SyncCacheViewAuthenticPixels(annotate_view,exception) == MagickFalse)
624 annotate_view=DestroyCacheView(annotate_view);
625 XDestroyImage(annotate_ximage);
627 Determine annotate geometry.
629 (void) XParseGeometry(annotate_info->geometry,&x,&y,&width,&height);
630 if ((width != (unsigned int) annotate_image->columns) ||
631 (height != (unsigned int) annotate_image->rows))
634 image_geometry[MaxTextExtent];
639 (void) FormatLocaleString(image_geometry,MaxTextExtent,"%ux%u",
641 (void) TransformImage(&annotate_image,(char *) NULL,image_geometry,
644 if (annotate_info->degrees != 0.0)
658 rotate_image=RotateImage(annotate_image,annotate_info->degrees,exception);
659 if (rotate_image == (Image *) NULL)
661 annotate_image=DestroyImage(annotate_image);
662 annotate_image=rotate_image;
664 Annotation is relative to the degree of rotation.
666 normalized_degrees=annotate_info->degrees;
667 while (normalized_degrees < -45.0)
668 normalized_degrees+=360.0;
669 for (rotations=0; normalized_degrees > 45.0; rotations++)
670 normalized_degrees-=90.0;
671 switch (rotations % 4)
681 x-=(int) annotate_image->columns/2;
682 y+=(int) annotate_image->columns/2;
690 x=x-(int) annotate_image->columns;
698 x=x-(int) annotate_image->columns/2;
699 y=y-(int) (annotate_image->rows-(annotate_image->columns/2));
705 Composite text onto the image.
707 (void) XParseGeometry(annotate_info->geometry,&x,&y,&width,&height);
709 (void) CompositeImage(image,annotate_image->matte != MagickFalse ?
710 OverCompositeOp : CopyCompositeOp,annotate_image,(ssize_t) x,(ssize_t) y,
713 annotate_image=DestroyImage(annotate_image);
718 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
722 % X B e s t F o n t %
726 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
728 % XBestFont() returns the "best" font. "Best" is defined as a font specified
729 % in the X resource database or a font such that the text width displayed
730 % with the font does not exceed the specified maximum width.
732 % The format of the XBestFont method is:
734 % XFontStruct *XBestFont(Display *display,
735 % const XResourceInfo *resource_info,const MagickBooleanType text_font)
737 % A description of each parameter follows:
739 % o font: XBestFont returns a pointer to a XFontStruct structure.
741 % o display: Specifies a connection to an X server; returned from
744 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
746 % o text_font: True is font should be mono-spaced (typewriter style).
750 static char **FontToList(char *font)
765 if (font == (char *) NULL)
766 return((char **) NULL);
768 Convert string to an ASCII list.
771 for (p=font; *p != '\0'; p++)
772 if ((*p == ':') || (*p == ';') || (*p == ','))
774 fontlist=(char **) AcquireQuantumMemory((size_t) fonts+1UL,sizeof(*fontlist));
775 if (fontlist == (char **) NULL)
777 ThrowXWindowFatalException(ResourceLimitError,"MemoryAllocationFailed",
779 return((char **) NULL);
782 for (i=0; i < (int) fonts; i++)
784 for (q=p; *q != '\0'; q++)
785 if ((*q == ':') || (*q == ';') || (*q == ','))
787 fontlist[i]=(char *) AcquireQuantumMemory((size_t) (q-p)+1UL,
788 sizeof(*fontlist[i]));
789 if (fontlist[i] == (char *) NULL)
791 ThrowXWindowFatalException(ResourceLimitError,"MemoryAllocationFailed",
793 return((char **) NULL);
795 (void) CopyMagickString(fontlist[i],p,(size_t) (q-p+1));
798 fontlist[i]=(char *) NULL;
802 MagickPrivate XFontStruct *XBestFont(Display *display,
803 const XResourceInfo *resource_info,const MagickBooleanType text_font)
808 "-*-helvetica-medium-r-normal--12-*-*-*-*-*-iso8859-1",
809 "-*-arial-medium-r-normal--12-*-*-*-*-*-iso8859-1",
810 "-*-helvetica-medium-r-normal--12-*-*-*-*-*-iso8859-15",
811 "-*-arial-medium-r-normal--12-*-*-*-*-*-iso8859-15",
812 "-*-helvetica-medium-r-normal--12-*-*-*-*-*-*-*",
813 "-*-arial-medium-r-normal--12-*-*-*-*-*-*-*",
820 "-*-courier-medium-r-normal-*-12-*-*-*-*-*-iso8859-1",
821 "-*-courier-medium-r-normal-*-12-*-*-*-*-*-iso8859-15",
822 "-*-fixed-medium-r-normal-*-12-*-*-*-*-*-*-*",
836 font_info=(XFontStruct *) NULL;
837 font_name=resource_info->font;
838 if (text_font != MagickFalse)
839 font_name=resource_info->text_font;
840 if ((font_name != (char *) NULL) && (*font_name != '\0'))
849 Load preferred font specified in the X resource database.
851 fontlist=FontToList(font_name);
852 if (fontlist != (char **) NULL)
854 for (i=0; fontlist[i] != (char *) NULL; i++)
856 if (font_info == (XFontStruct *) NULL)
857 font_info=XLoadQueryFont(display,fontlist[i]);
858 fontlist[i]=DestroyString(fontlist[i]);
860 fontlist=(char **) RelinquishMagickMemory(fontlist);
862 if (font_info == (XFontStruct *) NULL)
863 ThrowXWindowFatalException(XServerError,"UnableToLoadFont",font_name);
866 Load fonts from list of fonts until one is found.
869 if (text_font != MagickFalse)
871 if (XDisplayHeight(display,XDefaultScreen(display)) >= 748)
873 while (*p != (char *) NULL)
875 if (font_info != (XFontStruct *) NULL)
877 font_info=XLoadQueryFont(display,(char *) *p);
884 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
888 % X B e s t I c o n S i z e %
892 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
894 % XBestIconSize() returns the "best" icon size. "Best" is defined as an icon
895 % size that maintains the aspect ratio of the image. If the window manager
896 % has preferred icon sizes, one of the preferred sizes is used.
898 % The format of the XBestIconSize method is:
900 % void XBestIconSize(Display *display,XWindowInfo *window,Image *image)
902 % A description of each parameter follows:
904 % o display: Specifies a connection to an X server; returned from
907 % o image: the image.
910 MagickPrivate void XBestIconSize(Display *display,XWindowInfo *window,
934 Determine if the window manager has specified preferred icon sizes.
936 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
937 assert(display != (Display *) NULL);
938 assert(window != (XWindowInfo *) NULL);
939 assert(image != (Image *) NULL);
940 window->width=MaxIconSize;
941 window->height=MaxIconSize;
942 icon_size=(XIconSize *) NULL;
944 root_window=XRootWindow(display,window->screen);
945 if (XGetIconSizes(display,root_window,&size_list,&number_sizes) != 0)
946 if ((number_sizes > 0) && (size_list != (XIconSize *) NULL))
948 if (icon_size == (XIconSize *) NULL)
951 Window manager does not restrict icon size.
953 icon_size=XAllocIconSize();
954 if (icon_size == (XIconSize *) NULL)
956 ThrowXWindowFatalException(ResourceLimitError,
957 "MemoryAllocationFailed",image->filename);
960 icon_size->min_width=1;
961 icon_size->max_width=MaxIconSize;
962 icon_size->min_height=1;
963 icon_size->max_height=MaxIconSize;
964 icon_size->width_inc=1;
965 icon_size->height_inc=1;
968 Determine aspect ratio of image.
970 width=(unsigned int) image->columns;
971 height=(unsigned int) image->rows;
973 if (window->crop_geometry)
974 (void) XParseGeometry(window->crop_geometry,&i,&i,&width,&height);
976 Look for an icon size that maintains the aspect ratio of image.
978 scale_factor=(MagickRealType) icon_size->max_width/width;
979 if (scale_factor > ((MagickRealType) icon_size->max_height/height))
980 scale_factor=(MagickRealType) icon_size->max_height/height;
981 icon_width=(unsigned int) icon_size->min_width;
982 while ((int) icon_width < icon_size->max_width)
984 if (icon_width >= (unsigned int) (scale_factor*width+0.5))
986 icon_width+=icon_size->width_inc;
988 icon_height=(unsigned int) icon_size->min_height;
989 while ((int) icon_height < icon_size->max_height)
991 if (icon_height >= (unsigned int) (scale_factor*height+0.5))
993 icon_height+=icon_size->height_inc;
995 (void) XFree((void *) icon_size);
996 window->width=icon_width;
997 window->height=icon_height;
1001 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1005 % X B e s t P i x e l %
1009 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1011 % XBestPixel() returns a pixel from an array of pixels that is closest to the
1012 % requested color. If the color array is NULL, the colors are obtained from
1015 % The format of the XBestPixel method is:
1017 % void XBestPixel(Display *display,const Colormap colormap,XColor *colors,
1018 % unsigned int number_colors,XColor *color)
1020 % A description of each parameter follows:
1022 % o pixel: XBestPixel returns the pixel value closest to the requested
1025 % o display: Specifies a connection to an X server; returned from
1028 % o colormap: Specifies the ID of the X server colormap.
1030 % o colors: Specifies an array of XColor structures.
1032 % o number_colors: Specifies the number of XColor structures in the
1033 % color definition array.
1035 % o color: Specifies the desired RGB value to find in the colors array.
1038 MagickPrivate void XBestPixel(Display *display,const Colormap colormap,
1039 XColor *colors,unsigned int number_colors,XColor *color)
1050 register MagickRealType
1061 Find closest representation for the requested RGB color.
1063 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1064 assert(display != (Display *) NULL);
1065 assert(color != (XColor *) NULL);
1066 status=XAllocColor(display,colormap,color);
1067 if (status != False)
1069 query_server=colors == (XColor *) NULL ? MagickTrue : MagickFalse;
1070 if (query_server != MagickFalse)
1073 Read X server colormap.
1075 colors=(XColor *) AcquireQuantumMemory(number_colors,sizeof(*colors));
1076 if (colors == (XColor *) NULL)
1078 ThrowXWindowFatalException(ResourceLimitError,
1079 "MemoryAllocationFailed","...");
1082 for (i=0; i < (int) number_colors; i++)
1083 colors[i].pixel=(size_t) i;
1084 if (number_colors > 256)
1086 (void) XQueryColors(display,colormap,colors,(int) number_colors);
1088 min_distance=3.0*((MagickRealType) QuantumRange+1.0)*((MagickRealType)
1091 for (i=0; i < (int) number_colors; i++)
1093 pixel.red=colors[i].red-(MagickRealType) color->red;
1094 distance=pixel.red*pixel.red;
1095 if (distance > min_distance)
1097 pixel.green=colors[i].green-(MagickRealType) color->green;
1098 distance+=pixel.green*pixel.green;
1099 if (distance > min_distance)
1101 pixel.blue=colors[i].blue-(MagickRealType) color->blue;
1102 distance+=pixel.blue*pixel.blue;
1103 if (distance > min_distance)
1105 min_distance=distance;
1106 color->pixel=colors[i].pixel;
1109 (void) XAllocColor(display,colormap,&colors[j]);
1110 if (query_server != MagickFalse)
1111 colors=(XColor *) RelinquishMagickMemory(colors);
1115 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1119 % X B e s t V i s u a l I n f o %
1123 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1125 % XBestVisualInfo() returns visual information for a visual that is the "best"
1126 % the server supports. "Best" is defined as:
1128 % 1. Restrict the visual list to those supported by the default screen.
1130 % 2. If a visual type is specified, restrict the visual list to those of
1133 % 3. If a map type is specified, choose the visual that matches the id
1134 % specified by the Standard Colormap.
1136 % 4 From the list of visuals, choose one that can display the most
1137 % simultaneous colors. If more than one visual can display the same
1138 % number of simultaneous colors, one is chosen based on a rank.
1140 % The format of the XBestVisualInfo method is:
1142 % XVisualInfo *XBestVisualInfo(Display *display,
1143 % XStandardColormap *map_info,XResourceInfo *resource_info)
1145 % A description of each parameter follows:
1147 % o visual_info: XBestVisualInfo returns a pointer to a X11 XVisualInfo
1150 % o display: Specifies a connection to an X server; returned from
1153 % o map_info: If map_type is specified, this structure is initialized
1154 % with info from the Standard Colormap.
1156 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
1160 static inline int MagickMax(const int x,const int y)
1167 static inline size_t MagickMin(const unsigned int x,
1168 const unsigned int y)
1175 MagickPrivate XVisualInfo *XBestVisualInfo(Display *display,
1176 XStandardColormap *map_info,XResourceInfo *resource_info)
1178 #define MaxStandardColormaps 7
1179 #define XVisualColormapSize(visual_info) MagickMin((unsigned int) (\
1180 (visual_info->klass == TrueColor) || (visual_info->klass == DirectColor) ? \
1181 visual_info->red_mask | visual_info->green_mask | visual_info->blue_mask : \
1182 (unsigned int) visual_info->colormap_size),1U << visual_info->depth)
1208 Restrict visual search by screen number.
1210 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1211 assert(display != (Display *) NULL);
1212 assert(map_info != (XStandardColormap *) NULL);
1213 assert(resource_info != (XResourceInfo *) NULL);
1214 map_type=resource_info->map_type;
1215 visual_type=resource_info->visual_type;
1216 visual_mask=VisualScreenMask;
1217 visual_template.screen=XDefaultScreen(display);
1218 visual_template.depth=XDefaultDepth(display,XDefaultScreen(display));
1220 if ((resource_info->immutable != MagickFalse) && (resource_info->colors != 0))
1221 if (resource_info->colors <= (one << (size_t) visual_template.depth))
1222 visual_mask|=VisualDepthMask;
1223 if (visual_type != (char *) NULL)
1226 Restrict visual search by class or visual id.
1228 if (LocaleCompare("staticgray",visual_type) == 0)
1230 visual_mask|=VisualClassMask;
1231 visual_template.klass=StaticGray;
1234 if (LocaleCompare("grayscale",visual_type) == 0)
1236 visual_mask|=VisualClassMask;
1237 visual_template.klass=GrayScale;
1240 if (LocaleCompare("staticcolor",visual_type) == 0)
1242 visual_mask|=VisualClassMask;
1243 visual_template.klass=StaticColor;
1246 if (LocaleCompare("pseudocolor",visual_type) == 0)
1248 visual_mask|=VisualClassMask;
1249 visual_template.klass=PseudoColor;
1252 if (LocaleCompare("truecolor",visual_type) == 0)
1254 visual_mask|=VisualClassMask;
1255 visual_template.klass=TrueColor;
1258 if (LocaleCompare("directcolor",visual_type) == 0)
1260 visual_mask|=VisualClassMask;
1261 visual_template.klass=DirectColor;
1264 if (LocaleCompare("default",visual_type) == 0)
1266 visual_mask|=VisualIDMask;
1267 visual_template.visualid=XVisualIDFromVisual(
1268 XDefaultVisual(display,XDefaultScreen(display)));
1271 if (isdigit((int) ((unsigned char) *visual_type)) != 0)
1273 visual_mask|=VisualIDMask;
1274 visual_template.visualid=
1275 strtol(visual_type,(char **) NULL,0);
1278 ThrowXWindowFatalException(XServerError,
1279 "UnrecognizedVisualSpecifier",visual_type);
1282 Get all visuals that meet our criteria so far.
1285 visual_list=XGetVisualInfo(display,visual_mask,&visual_template,
1287 visual_mask=VisualScreenMask | VisualIDMask;
1288 if ((number_visuals == 0) || (visual_list == (XVisualInfo *) NULL))
1291 Failed to get visual; try using the default visual.
1293 ThrowXWindowFatalException(XServerWarning,"UnableToGetVisual",
1295 visual_template.visualid=XVisualIDFromVisual(XDefaultVisual(display,
1296 XDefaultScreen(display)));
1297 visual_list=XGetVisualInfo(display,visual_mask,&visual_template,
1299 if ((number_visuals == 0) || (visual_list == (XVisualInfo *) NULL))
1300 return((XVisualInfo *) NULL);
1301 ThrowXWindowFatalException(XServerWarning,"UsingDefaultVisual",
1302 XVisualClassName(visual_list->klass));
1304 resource_info->color_recovery=MagickFalse;
1305 if ((map_info != (XStandardColormap *) NULL) && (map_type != (char *) NULL))
1311 map_name[MaxTextExtent];
1327 Choose a visual associated with a standard colormap.
1329 root_window=XRootWindow(display,XDefaultScreen(display));
1331 if (LocaleCompare(map_type,"list") != 0)
1334 User specified Standard Colormap.
1336 (void) FormatLocaleString((char *) map_name,MaxTextExtent,
1337 "RGB_%s_MAP",map_type);
1338 LocaleUpper(map_name);
1339 map_property=XInternAtom(display,(char *) map_name,MagickTrue);
1340 if (map_property != (Atom) NULL)
1341 status=XGetRGBColormaps(display,root_window,&map_list,&number_maps,
1347 *colormap[MaxStandardColormaps]=
1349 "_HP_RGB_SMOOTH_MAP_LIST",
1359 Choose a standard colormap from a list.
1361 for (i=0; i < MaxStandardColormaps; i++)
1363 map_property=XInternAtom(display,(char *) colormap[i],MagickTrue);
1364 if (map_property == (Atom) NULL)
1366 status=XGetRGBColormaps(display,root_window,&map_list,&number_maps,
1368 if (status != False)
1371 resource_info->color_recovery=i == 0 ? MagickTrue : MagickFalse;
1373 if (status == False)
1375 ThrowXWindowFatalException(XServerError,"UnableToGetStandardColormap",
1377 return((XVisualInfo *) NULL);
1380 Search all Standard Colormaps and visuals for ids that match.
1382 *map_info=map_list[0];
1383 #if !defined(PRE_R4_ICCCM)
1384 visual_template.visualid=XVisualIDFromVisual(visual_list[0].visual);
1385 for (i=0; i < number_maps; i++)
1386 for (j=0; j < number_visuals; j++)
1387 if (map_list[i].visualid ==
1388 XVisualIDFromVisual(visual_list[j].visual))
1390 *map_info=map_list[i];
1391 visual_template.visualid=XVisualIDFromVisual(
1392 visual_list[j].visual);
1395 if (map_info->visualid != visual_template.visualid)
1397 ThrowXWindowFatalException(XServerError,
1398 "UnableToMatchVisualToStandardColormap",map_type);
1399 return((XVisualInfo *) NULL);
1402 if (map_info->colormap == (Colormap) NULL)
1404 ThrowXWindowFatalException(XServerError,
1405 "StandardColormapIsNotInitialized",map_type);
1406 return((XVisualInfo *) NULL);
1408 (void) XFree((void *) map_list);
1412 static const unsigned int
1427 Pick one visual that displays the most simultaneous colors.
1429 visual_info=visual_list;
1431 for (i=1; i < number_visuals; i++)
1434 if (XVisualColormapSize(p) > XVisualColormapSize(visual_info))
1437 if (XVisualColormapSize(p) == XVisualColormapSize(visual_info))
1438 if (rank[p->klass] > rank[visual_info->klass])
1441 visual_template.visualid=XVisualIDFromVisual(visual_info->visual);
1443 (void) XFree((void *) visual_list);
1445 Retrieve only one visual by its screen & id number.
1447 visual_info=XGetVisualInfo(display,visual_mask,&visual_template,
1449 if ((number_visuals == 0) || (visual_info == (XVisualInfo *) NULL))
1450 return((XVisualInfo *) NULL);
1451 return(visual_info);
1455 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1459 % X C h e c k D e f i n e C u r s o r %
1463 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1465 % XCheckDefineCursor() prevents cursor changes on the root window.
1467 % The format of the XXCheckDefineCursor method is:
1469 % XCheckDefineCursor(display,window,cursor)
1471 % A description of each parameter follows:
1473 % o display: Specifies a connection to an X server; returned from
1476 % o window: the window.
1478 % o cursor: the cursor.
1481 MagickPrivate int XCheckDefineCursor(Display *display,Window window,
1484 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1485 assert(display != (Display *) NULL);
1486 if (window == XRootWindow(display,XDefaultScreen(display)))
1488 return(XDefineCursor(display,window,cursor));
1492 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1496 % X C h e c k R e f r e s h W i n d o w s %
1500 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1502 % XCheckRefreshWindows() checks the X server for exposure events for a
1503 % particular window and updates the areassociated with the exposure event.
1505 % The format of the XCheckRefreshWindows method is:
1507 % void XCheckRefreshWindows(Display *display,XWindows *windows)
1509 % A description of each parameter follows:
1511 % o display: Specifies a connection to an X server; returned from
1514 % o windows: Specifies a pointer to a XWindows structure.
1517 MagickPrivate void XCheckRefreshWindows(Display *display,XWindows *windows)
1525 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1526 assert(display != (Display *) NULL);
1527 assert(windows != (XWindows *) NULL);
1528 XDelay(display,SuspendTime);
1529 id=windows->command.id;
1530 while (XCheckTypedWindowEvent(display,id,Expose,&event) != MagickFalse)
1531 (void) XCommandWidget(display,windows,(char const **) NULL,&event);
1532 id=windows->image.id;
1533 while (XCheckTypedWindowEvent(display,id,Expose,&event) != MagickFalse)
1534 XRefreshWindow(display,&windows->image,&event);
1535 XDelay(display,SuspendTime << 1);
1536 id=windows->command.id;
1537 while (XCheckTypedWindowEvent(display,id,Expose,&event) != MagickFalse)
1538 (void) XCommandWidget(display,windows,(char const **) NULL,&event);
1539 id=windows->image.id;
1540 while (XCheckTypedWindowEvent(display,id,Expose,&event) != MagickFalse)
1541 XRefreshWindow(display,&windows->image,&event);
1545 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1549 % X C l i e n t M e s s a g e %
1553 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1555 % XClientMessage() sends a reason to a window with XSendEvent. The reason is
1556 % initialized with a particular protocol type and atom.
1558 % The format of the XClientMessage function is:
1560 % XClientMessage(display,window,protocol,reason,timestamp)
1562 % A description of each parameter follows:
1564 % o display: Specifies a pointer to the Display structure; returned from
1567 % o window: Specifies a pointer to a Window structure.
1569 % o protocol: Specifies an atom value.
1571 % o reason: Specifies an atom value which is the reason to send.
1573 % o timestamp: Specifies a value of type Time.
1576 MagickPrivate void XClientMessage(Display *display,const Window window,
1577 const Atom protocol,const Atom reason,const Time timestamp)
1582 assert(display != (Display *) NULL);
1583 client_event.type=ClientMessage;
1584 client_event.window=window;
1585 client_event.message_type=protocol;
1586 client_event.format=32;
1587 client_event.data.l[0]=(long) reason;
1588 client_event.data.l[1]=(long) timestamp;
1589 (void) XSendEvent(display,window,MagickFalse,NoEventMask,(XEvent *) &client_event);
1593 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1597 + X C l i e n t W i n d o w %
1601 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1603 % XClientWindow() finds a window, at or below the specified window, which has
1604 % a WM_STATE property. If such a window is found, it is returned, otherwise
1605 % the argument window is returned.
1607 % The format of the XClientWindow function is:
1609 % client_window=XClientWindow(display,target_window)
1611 % A description of each parameter follows:
1613 % o client_window: XClientWindow returns a window, at or below the specified
1614 % window, which has a WM_STATE property otherwise the argument
1615 % target_window is returned.
1617 % o display: Specifies a pointer to the Display structure; returned from
1620 % o target_window: Specifies the window to find a WM_STATE property.
1623 static Window XClientWindow(Display *display,Window target_window)
1645 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1646 assert(display != (Display *) NULL);
1647 state=XInternAtom(display,"WM_STATE",MagickTrue);
1648 if (state == (Atom) NULL)
1649 return(target_window);
1651 status=XGetWindowProperty(display,target_window,state,0L,0L,MagickFalse,
1652 (Atom) AnyPropertyType,&type,&format,&number_items,&after,&data);
1653 if ((status == Success) && (type != (Atom) NULL))
1654 return(target_window);
1655 client_window=XWindowByProperty(display,target_window,state);
1656 if (client_window == (Window) NULL)
1657 return(target_window);
1658 return(client_window);
1662 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1666 + X C o m p o n e n t T e r m i n u s %
1670 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1672 % XComponentTerminus() destroys the module component.
1674 % The format of the XComponentTerminus method is:
1676 % XComponentTerminus(void)
1679 MagickPrivate void XComponentTerminus(void)
1681 DestroyXResources();
1685 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1689 % X C o n f i g u r e I m a g e C o l o r m a p %
1693 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1695 % XConfigureImageColormap() creates a new X colormap.
1697 % The format of the XConfigureImageColormap method is:
1699 % void XConfigureImageColormap(Display *display,
1700 % XResourceInfo *resource_info,XWindows *windows,Image *image,
1701 % ExceptionInfo *exception)
1703 % A description of each parameter follows:
1705 % o display: Specifies a connection to an X server; returned from
1708 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
1710 % o windows: Specifies a pointer to a XWindows structure.
1712 % o image: the image.
1714 % o exception: return any errors or warnings in this structure.
1717 MagickPrivate void XConfigureImageColormap(Display *display,
1718 XResourceInfo *resource_info,XWindows *windows,Image *image,
1719 ExceptionInfo *exception)
1725 Make standard colormap.
1727 XSetCursorState(display,windows,MagickTrue);
1728 XCheckRefreshWindows(display,windows);
1729 XMakeStandardColormap(display,windows->visual_info,resource_info,image,
1730 windows->map_info,windows->pixel_info,exception);
1731 colormap=windows->map_info->colormap;
1732 (void) XSetWindowColormap(display,windows->image.id,colormap);
1733 (void) XSetWindowColormap(display,windows->command.id,colormap);
1734 (void) XSetWindowColormap(display,windows->widget.id,colormap);
1735 if (windows->magnify.mapped != MagickFalse)
1736 (void) XSetWindowColormap(display,windows->magnify.id,colormap);
1737 if (windows->pan.mapped != MagickFalse)
1738 (void) XSetWindowColormap(display,windows->pan.id,colormap);
1739 XSetCursorState(display,windows,MagickFalse);
1740 XClientMessage(display,windows->image.id,windows->im_protocols,
1741 windows->im_update_colormap,CurrentTime);
1745 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1749 % X C o n s t r a i n W i n d o w P o s i t i o n %
1753 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1755 % XConstrainWindowPosition() assures a window is positioned within the X
1756 % server boundaries.
1758 % The format of the XConstrainWindowPosition method is:
1760 % void XConstrainWindowPosition(Display *display,XWindowInfo *window_info)
1762 % A description of each parameter follows:
1764 % o display: Specifies a pointer to the Display structure; returned from
1767 % o window_info: Specifies a pointer to a XWindowInfo structure.
1770 MagickPrivate void XConstrainWindowPosition(Display *display,
1771 XWindowInfo *window_info)
1776 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1777 assert(display != (Display *) NULL);
1778 assert(window_info != (XWindowInfo *) NULL);
1779 limit=XDisplayWidth(display,window_info->screen)-window_info->width;
1780 if (window_info->x < 0)
1783 if (window_info->x > (int) limit)
1784 window_info->x=(int) limit;
1785 limit=XDisplayHeight(display,window_info->screen)-window_info->height;
1786 if (window_info->y < 0)
1789 if (window_info->y > limit)
1790 window_info->y=limit;
1794 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1802 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1804 % XDelay() suspends program execution for the number of milliseconds
1807 % The format of the Delay method is:
1809 % void XDelay(Display *display,const size_t milliseconds)
1811 % A description of each parameter follows:
1813 % o display: Specifies a pointer to the Display structure; returned from
1816 % o milliseconds: Specifies the number of milliseconds to delay before
1820 MagickPrivate void XDelay(Display *display,const size_t milliseconds)
1822 assert(display != (Display *) NULL);
1823 (void) XFlush(display);
1824 MagickDelay(milliseconds);
1828 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1832 % X D e s t r o y R e s o u r c e I n f o %
1836 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1838 % XDestroyResourceInfo() frees memory associated with the XResourceInfo
1841 % The format of the XDestroyResourceInfo method is:
1843 % void XDestroyResourceInfo(XResourceInfo *resource_info)
1845 % A description of each parameter follows:
1847 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
1850 MagickExport void XDestroyResourceInfo(XResourceInfo *resource_info)
1852 if (resource_info->image_geometry != (char *) NULL)
1853 resource_info->image_geometry=(char *)
1854 RelinquishMagickMemory(resource_info->image_geometry);
1855 if (resource_info->quantize_info != (QuantizeInfo *) NULL)
1856 resource_info->quantize_info=DestroyQuantizeInfo(
1857 resource_info->quantize_info);
1858 if (resource_info->client_name != (char *) NULL)
1859 resource_info->client_name=(char *)
1860 RelinquishMagickMemory(resource_info->client_name);
1861 if (resource_info->name != (char *) NULL)
1862 resource_info->name=DestroyString(resource_info->name);
1863 (void) ResetMagickMemory(resource_info,0,sizeof(*resource_info));
1867 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1871 % X D e s t r o y W i n d o w C o l o r s %
1875 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1877 % XDestroyWindowColors() frees X11 color resources previously saved on a
1878 % window by XRetainWindowColors or programs like xsetroot.
1880 % The format of the XDestroyWindowColors method is:
1882 % void XDestroyWindowColors(Display *display,Window window)
1884 % A description of each parameter follows:
1886 % o display: Specifies a connection to an X server; returned from
1889 % o window: Specifies a pointer to a Window structure.
1892 MagickPrivate void XDestroyWindowColors(Display *display,Window window)
1912 If there are previous resources on the root window, destroy them.
1914 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1915 assert(display != (Display *) NULL);
1916 property=XInternAtom(display,"_XSETROOT_ID",MagickFalse);
1917 if (property == (Atom) NULL)
1919 ThrowXWindowFatalException(XServerError,"UnableToCreateProperty",
1923 status=XGetWindowProperty(display,window,property,0L,1L,MagickTrue,
1924 (Atom) AnyPropertyType,&type,&format,&length,&after,&data);
1925 if (status != Success)
1927 if ((type == XA_PIXMAP) && (format == 32) && (length == 1) && (after == 0))
1929 (void) XKillClient(display,(XID) (*((Pixmap *) data)));
1930 (void) XDeleteProperty(display,window,property);
1933 (void) XFree((void *) data);
1937 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1941 % X D i s p l a y I m a g e I n f o %
1945 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1947 % XDisplayImageInfo() displays information about an X image.
1949 % The format of the XDisplayImageInfo method is:
1951 % void XDisplayImageInfo(Display *display,
1952 % const XResourceInfo *resource_info,XWindows *windows,Image *undo_image,
1953 % Image *image,ExceptionInfo *exception)
1955 % A description of each parameter follows:
1957 % o display: Specifies a connection to an X server; returned from
1960 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
1962 % o windows: Specifies a pointer to a XWindows structure.
1964 % o undo_image: the undo image.
1966 % o image: the image.
1968 % o exception: return any errors or warnings in this structure.
1971 MagickPrivate void XDisplayImageInfo(Display *display,
1972 const XResourceInfo *resource_info,XWindows *windows,Image *undo_image,
1973 Image *image,ExceptionInfo *exception)
1976 filename[MaxTextExtent],
1999 Write info about the X server to a file.
2001 assert(display != (Display *) NULL);
2002 assert(resource_info != (XResourceInfo *) NULL);
2003 assert(windows != (XWindows *) NULL);
2004 assert(image != (Image *) NULL);
2006 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
2008 unique_file=AcquireUniqueFileResource(filename);
2009 if (unique_file != -1)
2010 file=fdopen(unique_file,"w");
2011 if ((unique_file == -1) || (file == (FILE *) NULL))
2013 XNoticeWidget(display,windows,"Unable to display image info",filename);
2016 if (resource_info->gamma_correct != MagickFalse)
2017 if (resource_info->display_gamma != (char *) NULL)
2018 (void) FormatLocaleFile(file,"Display\n gamma: %s\n\n",
2019 resource_info->display_gamma);
2021 Write info about the X image to a file.
2023 (void) FormatLocaleFile(file,"X\n visual: %s\n",
2024 XVisualClassName((int) windows->image.storage_class));
2025 (void) FormatLocaleFile(file," depth: %d\n",windows->image.ximage->depth);
2026 if (windows->visual_info->colormap_size != 0)
2027 (void) FormatLocaleFile(file," colormap size: %d\n",
2028 windows->visual_info->colormap_size);
2029 if (resource_info->colormap== SharedColormap)
2030 (void) FormatLocaleFile(file," colormap type: Shared\n");
2032 (void) FormatLocaleFile(file," colormap type: Private\n");
2033 (void) FormatLocaleFile(file," geometry: %dx%d\n",
2034 windows->image.ximage->width,windows->image.ximage->height);
2035 if (windows->image.crop_geometry != (char *) NULL)
2036 (void) FormatLocaleFile(file," crop geometry: %s\n",
2037 windows->image.crop_geometry);
2038 if (windows->image.pixmap == (Pixmap) NULL)
2039 (void) FormatLocaleFile(file," type: X Image\n");
2041 (void) FormatLocaleFile(file," type: Pixmap\n");
2042 if (windows->image.shape != MagickFalse)
2043 (void) FormatLocaleFile(file," non-rectangular shape: True\n");
2045 (void) FormatLocaleFile(file," non-rectangular shape: False\n");
2046 if (windows->image.shared_memory != MagickFalse)
2047 (void) FormatLocaleFile(file," shared memory: True\n");
2049 (void) FormatLocaleFile(file," shared memory: False\n");
2050 (void) FormatLocaleFile(file,"\n");
2051 if (resource_info->font != (char *) NULL)
2052 (void) FormatLocaleFile(file,"Font: %s\n\n",resource_info->font);
2053 if (resource_info->text_font != (char *) NULL)
2054 (void) FormatLocaleFile(file,"Text font: %s\n\n",resource_info->text_font);
2056 Write info about the undo cache to a file.
2059 for (levels=0; undo_image != (Image *) NULL; levels++)
2061 number_pixels=undo_image->list->columns*undo_image->list->rows;
2062 bytes+=number_pixels*sizeof(PixelInfo);
2063 undo_image=GetPreviousImageInList(undo_image);
2065 (void) FormatLocaleFile(file,"Undo Edit Cache\n levels: %u\n",levels);
2066 (void) FormatLocaleFile(file," bytes: %.20gmb\n",(double)
2067 ((bytes+(1 << 19)) >> 20));
2068 (void) FormatLocaleFile(file," limit: %.20gmb\n\n",(double)
2069 resource_info->undo_cache);
2071 Write info about the image to a file.
2073 (void) IdentifyImage(image,file,MagickTrue,exception);
2074 (void) fclose(file);
2075 text=FileToString(filename,~0,exception);
2076 (void) RelinquishUniqueFileResource(filename);
2077 if (text == (char *) NULL)
2079 XNoticeWidget(display,windows,"MemoryAllocationFailed",
2080 "UnableToDisplayImageInfo");
2083 textlist=StringToList(text);
2084 if (textlist != (char **) NULL)
2087 title[MaxTextExtent];
2090 Display information about the image in the Text View widget.
2092 (void) XWithdrawWindow(display,windows->info.id,windows->info.screen);
2093 (void) FormatLocaleString(title,MaxTextExtent,"Image Info: %s",
2095 XTextViewWidget(display,resource_info,windows,MagickTrue,title,
2096 (char const **) textlist);
2097 for (i=0; textlist[i] != (char *) NULL; i++)
2098 textlist[i]=DestroyString(textlist[i]);
2099 textlist=(char **) RelinquishMagickMemory(textlist);
2101 text=DestroyString(text);
2105 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2109 + X D i t h e r I m a g e %
2113 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2115 % XDitherImage() dithers the reference image as required by the HP Color
2116 % Recovery algorithm. The color values are quantized to 3 bits of red and
2117 % green, and 2 bits of blue (3/3/2) and can be used as indices into a 8-bit X
2118 % standard colormap.
2120 % The format of the XDitherImage method is:
2122 % void XDitherImage(Image *image,XImage *ximage,ExceptionInfo *exception)
2124 % A description of each parameter follows:
2126 % o image: the image.
2128 % o ximage: Specifies a pointer to a XImage structure; returned from
2131 % o exception: return any errors or warnings in this structure.
2134 static void XDitherImage(Image *image,XImage *ximage,ExceptionInfo *exception)
2136 static const short int
2139 {-16, 4, -1, 11,-14, 6, -3, 9,-15, 5, -2, 10,-13, 7, -4, 8},
2140 { 15, -5, 0,-12, 13, -7, 2,-10, 14, -6, 1,-11, 12, -8, 3, -9}
2142 dither_green[2][16]=
2144 { 11,-15, 7, -3, 8,-14, 4, -2, 10,-16, 6, -4, 9,-13, 5, -1},
2145 {-12, 14, -8, 2, -9, 13, -5, 1,-11, 15, -7, 3,-10, 12, -6, 0}
2149 { -3, 9,-13, 7, -1, 11,-15, 5, -4, 8,-14, 6, -2, 10,-16, 4},
2150 { 2,-10, 12, -8, 0,-12, 14, -6, 3, -9, 13, -7, 1,-11, 15, -5}
2166 register const Quantum
2186 Allocate and initialize dither maps.
2188 for (i=0; i < 2; i++)
2189 for (j=0; j < 16; j++)
2191 red_map[i][j]=(unsigned char *) AcquireQuantumMemory(256UL,
2193 green_map[i][j]=(unsigned char *) AcquireQuantumMemory(256UL,
2194 sizeof(*green_map));
2195 blue_map[i][j]=(unsigned char *) AcquireQuantumMemory(256UL,
2197 if ((red_map[i][j] == (unsigned char *) NULL) ||
2198 (green_map[i][j] == (unsigned char *) NULL) ||
2199 (blue_map[i][j] == (unsigned char *) NULL))
2201 ThrowXWindowFatalException(ResourceLimitError,
2202 "MemoryAllocationFailed",image->filename);
2207 Initialize dither tables.
2209 for (i=0; i < 2; i++)
2210 for (j=0; j < 16; j++)
2211 for (x=0; x < 256; x++)
2216 value+=dither_red[i][j];
2217 red_map[i][j][x]=(unsigned char)
2218 ((value < 0) ? 0 : (value > 255) ? 255 : value);
2222 value+=dither_green[i][j];
2223 green_map[i][j][x]=(unsigned char)
2224 ((value < 0) ? 0 : (value > 255) ? 255 : value);
2228 value+=((size_t) dither_blue[i][j] << 1);
2229 blue_map[i][j][x]=(unsigned char)
2230 ((value < 0) ? 0 : (value > 255) ? 255 : value);
2235 scanline_pad=(unsigned int) (ximage->bytes_per_line-
2236 ((size_t) (ximage->width*ximage->bits_per_pixel) >> 3));
2240 image_view=AcquireCacheView(image);
2241 for (y=0; y < (int) image->rows; y++)
2243 p=GetCacheViewVirtualPixels(image_view,0,(ssize_t) y,image->columns,1,
2245 if (p == (const Quantum *) NULL)
2247 for (x=0; x < (int) image->columns; x++)
2249 color.red=(double) ClampToQuantum((MagickRealType) (red_map[i][j][
2250 (int) ScaleQuantumToChar(GetPixelRed(image,p))] << 8));
2251 color.green=(double) ClampToQuantum((MagickRealType) (green_map[i][j][
2252 (int) ScaleQuantumToChar(GetPixelGreen(image,p))] << 8));
2253 color.blue=(double) ClampToQuantum((MagickRealType) (blue_map[i][j][
2254 (int) ScaleQuantumToChar(GetPixelBlue(image,p))] << 8));
2255 pixel=(size_t) (((size_t) color.red & 0xe0) |
2256 (((size_t) color.green & 0xe0) >> 3) |
2257 (((size_t) color.blue & 0xc0) >> 6));
2259 p+=GetPixelChannels(image);
2269 image_view=DestroyCacheView(image_view);
2271 Free allocated memory.
2273 for (i=0; i < 2; i++)
2274 for (j=0; j < 16; j++)
2276 green_map[i][j]=(unsigned char *) RelinquishMagickMemory(green_map[i][j]);
2277 blue_map[i][j]=(unsigned char *) RelinquishMagickMemory(blue_map[i][j]);
2278 red_map[i][j]=(unsigned char *) RelinquishMagickMemory(red_map[i][j]);
2283 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2287 % X D r a w I m a g e %
2291 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2293 % XDrawImage() draws a line on the image.
2295 % The format of the XDrawImage method is:
2297 % MagickBooleanType XDrawImage(Display *display,const XPixelInfo *pixel,
2298 % XDrawInfo *draw_info,Image *image,ExceptionInfo *exception)
2300 % A description of each parameter follows:
2302 % o display: Specifies a connection to an X server; returned from
2305 % o pixel: Specifies a pointer to a XPixelInfo structure.
2307 % o draw_info: Specifies a pointer to a XDrawInfo structure.
2309 % o image: the image.
2311 % o exception: return any errors or warnings in this structure.
2314 MagickPrivate MagickBooleanType XDrawImage(Display *display,
2315 const XPixelInfo *pixel,XDrawInfo *draw_info,Image *image,
2316 ExceptionInfo *exception)
2335 virtual_pixel[CompositePixelChannel];
2355 Initialize drawd image.
2357 assert(display != (Display *) NULL);
2358 assert(pixel != (XPixelInfo *) NULL);
2359 assert(draw_info != (XDrawInfo *) NULL);
2360 assert(image != (Image *) NULL);
2361 if (image->debug != MagickFalse)
2362 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2364 Initialize drawd pixmap.
2366 root_window=XRootWindow(display,XDefaultScreen(display));
2367 depth=(unsigned int) XDefaultDepth(display,XDefaultScreen(display));
2368 draw_pixmap=XCreatePixmap(display,root_window,draw_info->width,
2369 draw_info->height,depth);
2370 if (draw_pixmap == (Pixmap) NULL)
2371 return(MagickFalse);
2373 Initialize graphics info.
2375 context_values.background=(size_t) (~0);
2376 context_values.foreground=0;
2377 context_values.line_width=(int) draw_info->line_width;
2378 draw_context=XCreateGC(display,root_window,(size_t)
2379 (GCBackground | GCForeground | GCLineWidth),&context_values);
2380 if (draw_context == (GC) NULL)
2381 return(MagickFalse);
2385 (void) XFillRectangle(display,draw_pixmap,draw_context,0,0,draw_info->width,
2388 Draw line to pixmap.
2390 (void) XSetBackground(display,draw_context,0);
2391 (void) XSetForeground(display,draw_context,(size_t) (~0));
2392 if (draw_info->stipple != (Pixmap) NULL)
2394 (void) XSetFillStyle(display,draw_context,FillOpaqueStippled);
2395 (void) XSetStipple(display,draw_context,draw_info->stipple);
2397 switch (draw_info->element)
2402 (void) XDrawLines(display,draw_pixmap,draw_context,
2403 draw_info->coordinate_info,(int) draw_info->number_coordinates,
2409 (void) XDrawLine(display,draw_pixmap,draw_context,draw_info->line_info.x1,
2410 draw_info->line_info.y1,draw_info->line_info.x2,
2411 draw_info->line_info.y2);
2414 case RectangleElement:
2416 (void) XDrawRectangle(display,draw_pixmap,draw_context,
2417 (int) draw_info->rectangle_info.x,(int) draw_info->rectangle_info.y,
2418 (unsigned int) draw_info->rectangle_info.width,
2419 (unsigned int) draw_info->rectangle_info.height);
2422 case FillRectangleElement:
2424 (void) XFillRectangle(display,draw_pixmap,draw_context,
2425 (int) draw_info->rectangle_info.x,(int) draw_info->rectangle_info.y,
2426 (unsigned int) draw_info->rectangle_info.width,
2427 (unsigned int) draw_info->rectangle_info.height);
2431 case EllipseElement:
2433 (void) XDrawArc(display,draw_pixmap,draw_context,
2434 (int) draw_info->rectangle_info.x,(int) draw_info->rectangle_info.y,
2435 (unsigned int) draw_info->rectangle_info.width,
2436 (unsigned int) draw_info->rectangle_info.height,0,360*64);
2439 case FillCircleElement:
2440 case FillEllipseElement:
2442 (void) XFillArc(display,draw_pixmap,draw_context,
2443 (int) draw_info->rectangle_info.x,(int) draw_info->rectangle_info.y,
2444 (unsigned int) draw_info->rectangle_info.width,
2445 (unsigned int) draw_info->rectangle_info.height,0,360*64);
2448 case PolygonElement:
2453 coordinate_info=draw_info->coordinate_info;
2454 (void) XDrawLines(display,draw_pixmap,draw_context,coordinate_info,
2455 (int) draw_info->number_coordinates,CoordModeOrigin);
2456 (void) XDrawLine(display,draw_pixmap,draw_context,
2457 coordinate_info[draw_info->number_coordinates-1].x,
2458 coordinate_info[draw_info->number_coordinates-1].y,
2459 coordinate_info[0].x,coordinate_info[0].y);
2462 case FillPolygonElement:
2464 (void) XFillPolygon(display,draw_pixmap,draw_context,
2465 draw_info->coordinate_info,(int) draw_info->number_coordinates,Complex,
2470 (void) XFreeGC(display,draw_context);
2474 draw_ximage=XGetImage(display,draw_pixmap,0,0,draw_info->width,
2475 draw_info->height,AllPlanes,ZPixmap);
2476 if (draw_ximage == (XImage *) NULL)
2477 return(MagickFalse);
2478 (void) XFreePixmap(display,draw_pixmap);
2480 Initialize draw image.
2482 draw_image=AcquireImage((ImageInfo *) NULL,exception);
2483 if (draw_image == (Image *) NULL)
2484 return(MagickFalse);
2485 draw_image->columns=draw_info->width;
2486 draw_image->rows=draw_info->height;
2488 Transfer drawn X image to image.
2490 width=(unsigned int) image->columns;
2491 height=(unsigned int) image->rows;
2494 (void) XParseGeometry(draw_info->geometry,&x,&y,&width,&height);
2495 (void) GetOneVirtualPixel(image,(ssize_t) x,(ssize_t) y,virtual_pixel,
2497 draw_image->background_color.red=(double) virtual_pixel[RedPixelChannel];
2498 draw_image->background_color.green=(double) virtual_pixel[GreenPixelChannel];
2499 draw_image->background_color.blue=(double) virtual_pixel[BluePixelChannel];
2500 draw_image->background_color.alpha=(double) virtual_pixel[AlphaPixelChannel];
2501 if (SetImageStorageClass(draw_image,DirectClass,exception) == MagickFalse)
2502 return(MagickFalse);
2503 draw_image->matte=MagickTrue;
2504 draw_view=AcquireCacheView(draw_image);
2505 for (y=0; y < (int) draw_image->rows; y++)
2513 q=QueueCacheViewAuthenticPixels(draw_view,0,(ssize_t) y,draw_image->columns,
2515 if (q == (Quantum *) NULL)
2517 for (x=0; x < (int) draw_image->columns; x++)
2519 if (XGetPixel(draw_ximage,x,y) == 0)
2522 Set this pixel to the background color.
2524 SetPixelInfoPixel(draw_image,&draw_image->background_color,q);
2525 SetPixelAlpha(draw_image,(Quantum) (draw_info->stencil ==
2526 OpaqueStencil ? TransparentAlpha : OpaqueAlpha),q);
2531 Set this pixel to the pen color.
2533 SetPixelRed(draw_image,ScaleShortToQuantum(
2534 pixel->pen_color.red),q);
2535 SetPixelGreen(draw_image,ScaleShortToQuantum(
2536 pixel->pen_color.green),q);
2537 SetPixelBlue(draw_image,ScaleShortToQuantum(
2538 pixel->pen_color.blue),q);
2539 SetPixelAlpha(draw_image,(Quantum) (draw_info->stencil ==
2540 OpaqueStencil ? OpaqueAlpha : TransparentAlpha),q);
2542 q+=GetPixelChannels(draw_image);
2544 if (SyncCacheViewAuthenticPixels(draw_view,exception) == MagickFalse)
2547 draw_view=DestroyCacheView(draw_view);
2548 XDestroyImage(draw_ximage);
2550 Determine draw geometry.
2552 (void) XParseGeometry(draw_info->geometry,&x,&y,&width,&height);
2553 if ((width != (unsigned int) draw_image->columns) ||
2554 (height != (unsigned int) draw_image->rows))
2557 image_geometry[MaxTextExtent];
2562 (void) FormatLocaleString(image_geometry,MaxTextExtent,"%ux%u",
2564 (void) TransformImage(&draw_image,(char *) NULL,image_geometry,
2567 if (draw_info->degrees != 0.0)
2581 rotate_image=RotateImage(draw_image,draw_info->degrees,exception);
2582 if (rotate_image == (Image *) NULL)
2583 return(MagickFalse);
2584 draw_image=DestroyImage(draw_image);
2585 draw_image=rotate_image;
2587 Annotation is relative to the degree of rotation.
2589 normalized_degrees=draw_info->degrees;
2590 while (normalized_degrees < -45.0)
2591 normalized_degrees+=360.0;
2592 for (rotations=0; normalized_degrees > 45.0; rotations++)
2593 normalized_degrees-=90.0;
2594 switch (rotations % 4)
2604 x=x-(int) draw_image->columns/2;
2605 y=y+(int) draw_image->columns/2;
2613 x=x-(int) draw_image->columns;
2621 x=x-(int) draw_image->columns/2;
2622 y=y-(int) (draw_image->rows-(draw_image->columns/2));
2628 Composite text onto the image.
2630 draw_view=AcquireCacheView(draw_image);
2631 for (y=0; y < (int) draw_image->rows; y++)
2639 q=GetCacheViewAuthenticPixels(draw_view,0,(ssize_t) y,draw_image->columns,1,
2641 if (q == (Quantum *) NULL)
2643 for (x=0; x < (int) draw_image->columns; x++)
2645 if (GetPixelAlpha(image,q) != TransparentAlpha)
2646 SetPixelAlpha(draw_image,OpaqueAlpha,q);
2647 q+=GetPixelChannels(draw_image);
2649 if (SyncCacheViewAuthenticPixels(draw_view,exception) == MagickFalse)
2652 draw_view=DestroyCacheView(draw_view);
2653 (void) XParseGeometry(draw_info->geometry,&x,&y,&width,&height);
2654 if (draw_info->stencil == TransparentStencil)
2655 (void) CompositeImage(image,CopyAlphaCompositeOp,draw_image,(ssize_t) x,
2656 (ssize_t) y,exception);
2660 (void) CompositeImage(image,OverCompositeOp,draw_image,(ssize_t) x,
2661 (ssize_t) y,exception);
2664 draw_image=DestroyImage(draw_image);
2669 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2677 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2679 % XError() ignores BadWindow errors for XQueryTree and XGetWindowAttributes,
2680 % and ignores BadDrawable errors for XGetGeometry, and ignores BadValue errors
2681 % for XQueryColor. It returns MagickFalse in those cases. Otherwise it
2684 % The format of the XError function is:
2686 % int XError(display,error)
2688 % A description of each parameter follows:
2690 % o display: Specifies a pointer to the Display structure; returned from
2693 % o error: Specifies the error event.
2697 #if defined(__cplusplus) || defined(c_plusplus)
2701 MagickExport int XError(Display *display,XErrorEvent *error)
2703 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2704 assert(display != (Display *) NULL);
2705 assert(error != (XErrorEvent *) NULL);
2706 xerror_alert=MagickTrue;
2707 switch (error->request_code)
2711 if ((int) error->error_code == BadDrawable)
2712 return(MagickFalse);
2715 case X_GetWindowAttributes:
2718 if ((int) error->error_code == BadWindow)
2719 return(MagickFalse);
2724 if ((int) error->error_code == BadValue)
2725 return(MagickFalse);
2732 #if defined(__cplusplus) || defined(c_plusplus)
2737 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2741 % X F r e e R e s o u r c e s %
2745 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2747 % XFreeResources() frees X11 resources.
2749 % The format of the XFreeResources method is:
2751 % void XFreeResources(Display *display,XVisualInfo *visual_info,
2752 % XStandardColormap *map_info,XPixelInfo *pixel,XFontStruct *font_info,
2753 % XResourceInfo *resource_info,XWindowInfo *window_info)
2754 % resource_info,window_info)
2756 % A description of each parameter follows:
2758 % o display: Specifies a connection to an X server; returned from
2761 % o visual_info: Specifies a pointer to a X11 XVisualInfo structure;
2762 % returned from XGetVisualInfo.
2764 % o map_info: If map_type is specified, this structure is initialized
2765 % with info from the Standard Colormap.
2767 % o pixel: Specifies a pointer to a XPixelInfo structure.
2769 % o font_info: Specifies a pointer to a XFontStruct structure.
2771 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
2773 % o window_info: Specifies a pointer to a X11 XWindowInfo structure.
2776 MagickPrivate void XFreeResources(Display *display,XVisualInfo *visual_info,
2777 XStandardColormap *map_info,XPixelInfo *pixel,XFontStruct *font_info,
2778 XResourceInfo *resource_info,XWindowInfo *window_info)
2780 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2781 assert(display != (Display *) NULL);
2782 assert(resource_info != (XResourceInfo *) NULL);
2783 if (window_info != (XWindowInfo *) NULL)
2788 if (window_info->ximage != (XImage *) NULL)
2789 XDestroyImage(window_info->ximage);
2790 if (window_info->id != (Window) NULL)
2793 Free destroy window and free cursors.
2795 if (window_info->id != XRootWindow(display,visual_info->screen))
2796 (void) XDestroyWindow(display,window_info->id);
2797 if (window_info->annotate_context != (GC) NULL)
2798 (void) XFreeGC(display,window_info->annotate_context);
2799 if (window_info->highlight_context != (GC) NULL)
2800 (void) XFreeGC(display,window_info->highlight_context);
2801 if (window_info->widget_context != (GC) NULL)
2802 (void) XFreeGC(display,window_info->widget_context);
2803 if (window_info->cursor != (Cursor) NULL)
2804 (void) XFreeCursor(display,window_info->cursor);
2805 window_info->cursor=(Cursor) NULL;
2806 if (window_info->busy_cursor != (Cursor) NULL)
2807 (void) XFreeCursor(display,window_info->busy_cursor);
2808 window_info->busy_cursor=(Cursor) NULL;
2814 if (font_info != (XFontStruct *) NULL)
2816 (void) XFreeFont(display,font_info);
2817 font_info=(XFontStruct *) NULL;
2819 if (map_info != (XStandardColormap *) NULL)
2822 Free X Standard Colormap.
2824 if (resource_info->map_type == (char *) NULL)
2825 (void) XFreeStandardColormap(display,visual_info,map_info,pixel);
2826 (void) XFree((void *) map_info);
2831 if (visual_info != (XVisualInfo *) NULL)
2832 (void) XFree((void *) visual_info);
2833 if (resource_info->close_server != MagickFalse)
2834 (void) XCloseDisplay(display);
2838 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2842 % X F r e e S t a n d a r d C o l o r m a p %
2846 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2848 % XFreeStandardColormap() frees an X11 colormap.
2850 % The format of the XFreeStandardColormap method is:
2852 % void XFreeStandardColormap(Display *display,
2853 % const XVisualInfo *visual_info,XStandardColormap *map_info,
2854 % XPixelInfo *pixel)
2856 % A description of each parameter follows:
2858 % o display: Specifies a connection to an X server; returned from
2861 % o visual_info: Specifies a pointer to a X11 XVisualInfo structure;
2862 % returned from XGetVisualInfo.
2864 % o map_info: If map_type is specified, this structure is initialized
2865 % with info from the Standard Colormap.
2867 % o pixel: Specifies a pointer to a XPixelInfo structure.
2870 MagickPrivate void XFreeStandardColormap(Display *display,
2871 const XVisualInfo *visual_info,XStandardColormap *map_info,XPixelInfo *pixel)
2876 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2877 assert(display != (Display *) NULL);
2878 assert(visual_info != (XVisualInfo *) NULL);
2879 assert(map_info != (XStandardColormap *) NULL);
2880 (void) XFlush(display);
2881 if (map_info->colormap != (Colormap) NULL)
2883 if (map_info->colormap != XDefaultColormap(display,visual_info->screen))
2884 (void) XFreeColormap(display,map_info->colormap);
2886 if (pixel != (XPixelInfo *) NULL)
2887 if ((visual_info->klass != TrueColor) &&
2888 (visual_info->klass != DirectColor))
2889 (void) XFreeColors(display,map_info->colormap,pixel->pixels,
2890 (int) pixel->colors,0);
2892 map_info->colormap=(Colormap) NULL;
2893 if (pixel != (XPixelInfo *) NULL)
2895 if (pixel->pixels != (unsigned long *) NULL)
2896 pixel->pixels=(unsigned long *) RelinquishMagickMemory(pixel->pixels);
2897 pixel->pixels=(unsigned long *) NULL;
2902 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2906 % X G e t A n n o t a t e I n f o %
2910 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2912 % XGetAnnotateInfo() initializes the AnnotateInfo structure.
2914 % The format of the XGetAnnotateInfo method is:
2916 % void XGetAnnotateInfo(XAnnotateInfo *annotate_info)
2918 % A description of each parameter follows:
2920 % o annotate_info: Specifies a pointer to a XAnnotateInfo structure.
2923 MagickPrivate void XGetAnnotateInfo(XAnnotateInfo *annotate_info)
2926 Initialize annotate structure.
2928 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2929 assert(annotate_info != (XAnnotateInfo *) NULL);
2932 annotate_info->width=0;
2933 annotate_info->height=0;
2934 annotate_info->stencil=ForegroundStencil;
2935 annotate_info->degrees=0.0;
2936 annotate_info->font_info=(XFontStruct *) NULL;
2937 annotate_info->text=(char *) NULL;
2938 *annotate_info->geometry='\0';
2939 annotate_info->previous=(XAnnotateInfo *) NULL;
2940 annotate_info->next=(XAnnotateInfo *) NULL;
2941 (void) XSupportsLocale();
2942 (void) XSetLocaleModifiers("");
2946 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2950 % X G e t M a p I n f o %
2954 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2956 % XGetMapInfo() initializes the XStandardColormap structure.
2958 % The format of the XStandardColormap method is:
2960 % void XGetMapInfo(const XVisualInfo *visual_info,const Colormap colormap,
2961 % XStandardColormap *map_info)
2963 % A description of each parameter follows:
2965 % o colormap: Specifies the ID of the X server colormap.
2967 % o visual_info: Specifies a pointer to a X11 XVisualInfo structure;
2968 % returned from XGetVisualInfo.
2970 % o map_info: Specifies a pointer to a X11 XStandardColormap structure.
2973 MagickPrivate void XGetMapInfo(const XVisualInfo *visual_info,
2974 const Colormap colormap,XStandardColormap *map_info)
2977 Initialize map info.
2979 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2980 assert(visual_info != (XVisualInfo *) NULL);
2981 assert(map_info != (XStandardColormap *) NULL);
2982 map_info->colormap=colormap;
2983 map_info->red_max=visual_info->red_mask;
2984 map_info->red_mult=(size_t) (map_info->red_max != 0 ? 1 : 0);
2985 if (map_info->red_max != 0)
2986 while ((map_info->red_max & 0x01) == 0)
2988 map_info->red_max>>=1;
2989 map_info->red_mult<<=1;
2991 map_info->green_max=visual_info->green_mask;
2992 map_info->green_mult=(size_t) (map_info->green_max != 0 ? 1 : 0);
2993 if (map_info->green_max != 0)
2994 while ((map_info->green_max & 0x01) == 0)
2996 map_info->green_max>>=1;
2997 map_info->green_mult<<=1;
2999 map_info->blue_max=visual_info->blue_mask;
3000 map_info->blue_mult=(size_t) (map_info->blue_max != 0 ? 1 : 0);
3001 if (map_info->blue_max != 0)
3002 while ((map_info->blue_max & 0x01) == 0)
3004 map_info->blue_max>>=1;
3005 map_info->blue_mult<<=1;
3007 map_info->base_pixel=0;
3011 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3015 % X G e t P i x e l I n f o %
3019 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3021 % XGetPixelInfo() initializes the PixelInfo structure.
3023 % The format of the XGetPixelInfo method is:
3025 % void XGetPixelInfo(Display *display,const XVisualInfo *visual_info,
3026 % const XStandardColormap *map_info,const XResourceInfo *resource_info,
3027 % Image *image,XPixelInfo *pixel)
3030 % A description of each parameter follows:
3032 % o display: Specifies a connection to an X server; returned from
3035 % o visual_info: Specifies a pointer to a X11 XVisualInfo structure;
3036 % returned from XGetVisualInfo.
3038 % o map_info: If map_type is specified, this structure is initialized
3039 % with info from the Standard Colormap.
3041 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
3043 % o image: the image.
3045 % o pixel: Specifies a pointer to a XPixelInfo structure.
3048 MagickPrivate void XGetPixelInfo(Display *display,
3049 const XVisualInfo *visual_info,const XStandardColormap *map_info,
3050 const XResourceInfo *resource_info,Image *image,XPixelInfo *pixel)
3053 *PenColors[MaxNumberPens]=
3055 "#000000000000", /* black */
3056 "#00000000ffff", /* blue */
3057 "#0000ffffffff", /* cyan */
3058 "#0000ffff0000", /* green */
3059 "#bdbdbdbdbdbd", /* gray */
3060 "#ffff00000000", /* red */
3061 "#ffff0000ffff", /* magenta */
3062 "#ffffffff0000", /* yellow */
3063 "#ffffffffffff", /* white */
3064 "#bdbdbdbdbdbd", /* gray */
3065 "#bdbdbdbdbdbd" /* gray */
3081 Initialize pixel info.
3083 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3084 assert(display != (Display *) NULL);
3085 assert(visual_info != (XVisualInfo *) NULL);
3086 assert(map_info != (XStandardColormap *) NULL);
3087 assert(resource_info != (XResourceInfo *) NULL);
3088 assert(pixel != (XPixelInfo *) NULL);
3090 if (image != (Image *) NULL)
3091 if (image->storage_class == PseudoClass)
3092 pixel->colors=(ssize_t) image->colors;
3093 packets=(unsigned int)
3094 MagickMax((int) pixel->colors,visual_info->colormap_size)+MaxNumberPens;
3095 if (pixel->pixels != (unsigned long *) NULL)
3096 pixel->pixels=(unsigned long *) RelinquishMagickMemory(pixel->pixels);
3097 pixel->pixels=(unsigned long *) AcquireQuantumMemory(packets,
3098 sizeof(pixel->pixels));
3099 if (pixel->pixels == (unsigned long *) NULL)
3100 ThrowXWindowFatalException(ResourceLimitFatalError,"UnableToGetPixelInfo",
3103 Set foreground color.
3105 colormap=map_info->colormap;
3106 (void) XParseColor(display,colormap,(char *) ForegroundColor,
3107 &pixel->foreground_color);
3108 status=XParseColor(display,colormap,resource_info->foreground_color,
3109 &pixel->foreground_color);
3110 if (status == False)
3111 ThrowXWindowFatalException(XServerError,"ColorIsNotKnownToServer",
3112 resource_info->foreground_color);
3113 pixel->foreground_color.pixel=
3114 XStandardPixel(map_info,&pixel->foreground_color);
3115 pixel->foreground_color.flags=(char) (DoRed | DoGreen | DoBlue);
3117 Set background color.
3119 (void) XParseColor(display,colormap,"#d6d6d6d6d6d6",&pixel->background_color);
3120 status=XParseColor(display,colormap,resource_info->background_color,
3121 &pixel->background_color);
3122 if (status == False)
3123 ThrowXWindowFatalException(XServerError,"ColorIsNotKnownToServer",
3124 resource_info->background_color);
3125 pixel->background_color.pixel=
3126 XStandardPixel(map_info,&pixel->background_color);
3127 pixel->background_color.flags=(char) (DoRed | DoGreen | DoBlue);
3131 (void) XParseColor(display,colormap,(char *) BorderColor,
3132 &pixel->border_color);
3133 status=XParseColor(display,colormap,resource_info->border_color,
3134 &pixel->border_color);
3135 if (status == False)
3136 ThrowXWindowFatalException(XServerError,"ColorIsNotKnownToServer",
3137 resource_info->border_color);
3138 pixel->border_color.pixel=XStandardPixel(map_info,&pixel->border_color);
3139 pixel->border_color.flags=(char) (DoRed | DoGreen | DoBlue);
3143 pixel->matte_color=pixel->background_color;
3144 if (resource_info->matte_color != (char *) NULL)
3147 Matte color is specified as a X resource or command line argument.
3149 status=XParseColor(display,colormap,resource_info->matte_color,
3150 &pixel->matte_color);
3151 if (status == False)
3152 ThrowXWindowFatalException(XServerError,"ColorIsNotKnownToServer",
3153 resource_info->matte_color);
3154 pixel->matte_color.pixel=XStandardPixel(map_info,&pixel->matte_color);
3155 pixel->matte_color.flags=(char) (DoRed | DoGreen | DoBlue);
3158 Set highlight color.
3160 pixel->highlight_color.red=(unsigned short) ((
3161 pixel->matte_color.red*ScaleQuantumToShort(HighlightModulate))/65535L+
3162 (ScaleQuantumToShort((Quantum) (QuantumRange-HighlightModulate))));
3163 pixel->highlight_color.green=(unsigned short) ((
3164 pixel->matte_color.green*ScaleQuantumToShort(HighlightModulate))/65535L+
3165 (ScaleQuantumToShort((Quantum) (QuantumRange-HighlightModulate))));
3166 pixel->highlight_color.blue=(unsigned short) ((
3167 pixel->matte_color.blue*ScaleQuantumToShort(HighlightModulate))/65535L+
3168 (ScaleQuantumToShort((Quantum) (QuantumRange-HighlightModulate))));
3169 pixel->highlight_color.pixel=
3170 XStandardPixel(map_info,&pixel->highlight_color);
3171 pixel->highlight_color.flags=(char) (DoRed | DoGreen | DoBlue);
3175 pixel->shadow_color.red=(unsigned short) (((MagickRealType)
3176 pixel->matte_color.red*ScaleQuantumToShort(ShadowModulate))/65535L);
3177 pixel->shadow_color.green=(unsigned short) (((MagickRealType)
3178 pixel->matte_color.green*ScaleQuantumToShort(ShadowModulate))/65535L);
3179 pixel->shadow_color.blue=(unsigned short) (((MagickRealType)
3180 pixel->matte_color.blue*ScaleQuantumToShort(ShadowModulate))/65535L);
3181 pixel->shadow_color.pixel=XStandardPixel(map_info,&pixel->shadow_color);
3182 pixel->shadow_color.flags=(char) (DoRed | DoGreen | DoBlue);
3186 pixel->depth_color.red=(unsigned short) (((MagickRealType)
3187 pixel->matte_color.red*ScaleQuantumToShort(DepthModulate))/65535L);
3188 pixel->depth_color.green=(unsigned short) (((MagickRealType)
3189 pixel->matte_color.green*ScaleQuantumToShort(DepthModulate))/65535L);
3190 pixel->depth_color.blue=(unsigned short) (((MagickRealType)
3191 pixel->matte_color.blue*ScaleQuantumToShort(DepthModulate))/65535L);
3192 pixel->depth_color.pixel=XStandardPixel(map_info,&pixel->depth_color);
3193 pixel->depth_color.flags=(char) (DoRed | DoGreen | DoBlue);
3197 pixel->trough_color.red=(unsigned short) (((MagickRealType)
3198 pixel->matte_color.red*ScaleQuantumToShort(TroughModulate))/65535L);
3199 pixel->trough_color.green=(unsigned short) (((MagickRealType)
3200 pixel->matte_color.green*ScaleQuantumToShort(TroughModulate))/65535L);
3201 pixel->trough_color.blue=(unsigned short) (((MagickRealType)
3202 pixel->matte_color.blue*ScaleQuantumToShort(TroughModulate))/65535L);
3203 pixel->trough_color.pixel=XStandardPixel(map_info,&pixel->trough_color);
3204 pixel->trough_color.flags=(char) (DoRed | DoGreen | DoBlue);
3208 for (i=0; i < MaxNumberPens; i++)
3210 (void) XParseColor(display,colormap,(char *) PenColors[i],
3211 &pixel->pen_colors[i]);
3212 status=XParseColor(display,colormap,resource_info->pen_colors[i],
3213 &pixel->pen_colors[i]);
3214 if (status == False)
3215 ThrowXWindowFatalException(XServerError,"ColorIsNotKnownToServer",
3216 resource_info->pen_colors[i]);
3217 pixel->pen_colors[i].pixel=XStandardPixel(map_info,&pixel->pen_colors[i]);
3218 pixel->pen_colors[i].flags=(char) (DoRed | DoGreen | DoBlue);
3220 pixel->box_color=pixel->background_color;
3221 pixel->pen_color=pixel->foreground_color;
3224 if (image != (Image *) NULL)
3226 if ((resource_info->gamma_correct != MagickFalse) &&
3227 (image->gamma != 0.0))
3236 Initialize map relative to display and image gamma.
3238 flags=ParseGeometry(resource_info->display_gamma,&geometry_info);
3239 red_gamma=geometry_info.rho;
3240 green_gamma=geometry_info.sigma;
3241 if ((flags & SigmaValue) == 0)
3242 green_gamma=red_gamma;
3243 blue_gamma=geometry_info.xi;
3244 if ((flags & XiValue) == 0)
3245 blue_gamma=red_gamma;
3246 red_gamma*=image->gamma;
3247 green_gamma*=image->gamma;
3248 blue_gamma*=image->gamma;
3250 if (image->storage_class == PseudoClass)
3253 Initialize pixel array for images of type PseudoClass.
3255 for (i=0; i < (ssize_t) image->colors; i++)
3256 pixel->pixels[i]=XGammaPacket(map_info,image->colormap+i);
3257 for (i=0; i < MaxNumberPens; i++)
3258 pixel->pixels[image->colors+i]=pixel->pen_colors[i].pixel;
3259 pixel->colors+=MaxNumberPens;
3265 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3269 % X G e t R e s o u r c e C l a s s %
3273 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3275 % XGetResourceClass() queries the X server for the specified resource name or
3276 % class. If the resource name or class is not defined in the database, the
3277 % supplied default value is returned.
3279 % The format of the XGetResourceClass method is:
3281 % char *XGetResourceClass(XrmDatabase database,const char *client_name,
3282 % const char *keyword,char *resource_default)
3284 % A description of each parameter follows:
3286 % o database: Specifies a resource database; returned from
3287 % XrmGetStringDatabase.
3289 % o client_name: Specifies the application name used to retrieve resource
3290 % info from the X server database.
3292 % o keyword: Specifies the keyword of the value being retrieved.
3294 % o resource_default: Specifies the default value to return if the query
3295 % fails to find the specified keyword/class.
3298 MagickExport char *XGetResourceClass(XrmDatabase database,
3299 const char *client_name,const char *keyword,char *resource_default)
3302 resource_class[MaxTextExtent],
3303 resource_name[MaxTextExtent];
3314 if (database == (XrmDatabase) NULL)
3315 return(resource_default);
3316 *resource_name='\0';
3317 *resource_class='\0';
3318 if (keyword != (char *) NULL)
3325 Initialize resource keyword and class.
3327 (void) FormatLocaleString(resource_name,MaxTextExtent,"%s.%s",
3328 client_name,keyword);
3329 c=(int) (*client_name);
3330 if ((c >= XK_a) && (c <= XK_z))
3333 if ((c >= XK_agrave) && (c <= XK_odiaeresis))
3334 c-=(XK_agrave-XK_Agrave);
3336 if ((c >= XK_oslash) && (c <= XK_thorn))
3337 c-=(XK_oslash-XK_Ooblique);
3339 if ((k >= XK_a) && (k <= XK_z))
3342 if ((k >= XK_agrave) && (k <= XK_odiaeresis))
3343 k-=(XK_agrave-XK_Agrave);
3345 if ((k >= XK_oslash) && (k <= XK_thorn))
3346 k-=(XK_oslash-XK_Ooblique);
3347 (void) FormatLocaleString(resource_class,MaxTextExtent,"%c%s.%c%s",c,
3348 client_name+1,k,keyword+1);
3350 status=XrmGetResource(database,resource_name,resource_class,&resource_type,
3352 if (status == False)
3353 return(resource_default);
3354 return(resource_value.addr);
3358 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3362 % X G e t R e s o u r c e D a t a b a s e %
3366 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3368 % XGetResourceDatabase() creates a new resource database and initializes it.
3370 % The format of the XGetResourceDatabase method is:
3372 % XrmDatabase XGetResourceDatabase(Display *display,
3373 % const char *client_name)
3375 % A description of each parameter follows:
3377 % o database: XGetResourceDatabase() returns the database after it is
3380 % o display: Specifies a connection to an X server; returned from
3383 % o client_name: Specifies the application name used to retrieve resource
3384 % info from the X server database.
3387 MagickExport XrmDatabase XGetResourceDatabase(Display *display,
3388 const char *client_name)
3391 filename[MaxTextExtent];
3403 if (display == (Display *) NULL)
3404 return((XrmDatabase) NULL);
3405 assert(client_name != (char *) NULL);
3407 Initialize resource database.
3410 (void) XGetDefault(display,(char *) client_name,"dummy");
3411 resource_database=XrmGetDatabase(display);
3413 Combine application database.
3415 if (client_name != (char *) NULL)
3418 Get basename of client.
3420 p=client_name+(strlen(client_name)-1);
3421 while ((p > client_name) && (*p != '/'))
3426 c=(int) (*client_name);
3427 if ((c >= XK_a) && (c <= XK_z))
3430 if ((c >= XK_agrave) && (c <= XK_odiaeresis))
3431 c-=(XK_agrave-XK_Agrave);
3433 if ((c >= XK_oslash) && (c <= XK_thorn))
3434 c-=(XK_oslash-XK_Ooblique);
3435 #if defined(X11_APPLICATION_PATH)
3436 (void) FormatLocaleString(filename,MaxTextExtent,"%s%c%s",
3437 X11_APPLICATION_PATH,c,client_name+1);
3438 (void) XrmCombineFileDatabase(filename,&resource_database,MagickFalse);
3440 if (XResourceManagerString(display) != (char *) NULL)
3443 Combine server database.
3445 server_database=XrmGetStringDatabase(XResourceManagerString(display));
3446 XrmCombineDatabase(server_database,&resource_database,MagickFalse);
3449 Merge user preferences database.
3451 #if defined(X11_PREFERENCES_PATH)
3452 (void) FormatLocaleString(filename,MaxTextExtent,"%s%src",
3453 X11_PREFERENCES_PATH,client_name);
3454 ExpandFilename(filename);
3455 (void) XrmCombineFileDatabase(filename,&resource_database,MagickFalse);
3457 return(resource_database);
3461 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3465 % X G e t R e s o u r c e I n f o %
3469 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3471 % XGetResourceInfo(image_info,) initializes the ResourceInfo structure.
3473 % The format of the XGetResourceInfo method is:
3475 % void XGetResourceInfo(const ImageInfo *image_info,XrmDatabase database,
3476 % const char *client_name,XResourceInfo *resource_info)
3478 % A description of each parameter follows:
3480 % o image_info: the image info.
3482 % o database: Specifies a resource database; returned from
3483 % XrmGetStringDatabase.
3485 % o client_name: Specifies the application name used to retrieve
3486 % resource info from the X server database.
3488 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
3491 MagickExport void XGetResourceInfo(const ImageInfo *image_info,
3492 XrmDatabase database,const char *client_name,XResourceInfo *resource_info)
3499 Initialize resource info fields.
3501 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3502 assert(resource_info != (XResourceInfo *) NULL);
3503 (void) ResetMagickMemory(resource_info,0,sizeof(*resource_info));
3504 resource_info->resource_database=database;
3505 resource_info->image_info=(ImageInfo *) image_info;
3506 (void) SetImageInfoProgressMonitor(resource_info->image_info,
3507 XMagickProgressMonitor,(void *) NULL);
3508 resource_info->quantize_info=CloneQuantizeInfo((QuantizeInfo *) NULL);
3509 resource_info->close_server=MagickTrue;
3510 resource_info->client_name=AcquireString(client_name);
3511 resource_value=XGetResourceClass(database,client_name,"backdrop",
3513 resource_info->backdrop=IsMagickTrue(resource_value);
3514 resource_info->background_color=XGetResourceInstance(database,client_name,
3515 "background",(char *) "#d6d6d6d6d6d6");
3516 resource_info->border_color=XGetResourceInstance(database,client_name,
3517 "borderColor",BorderColor);
3518 resource_value=XGetResourceClass(database,client_name,"borderWidth",
3520 resource_info->border_width=(unsigned int) StringToUnsignedLong(
3522 resource_value=XGetResourceClass(database,client_name,"colormap",
3524 resource_info->colormap=UndefinedColormap;
3525 if (LocaleCompare("private",resource_value) == 0)
3526 resource_info->colormap=PrivateColormap;
3527 if (LocaleCompare("shared",resource_value) == 0)
3528 resource_info->colormap=SharedColormap;
3529 if (resource_info->colormap == UndefinedColormap)
3530 ThrowXWindowFatalException(OptionError,"UnrecognizedColormapType",
3532 resource_value=XGetResourceClass(database,client_name,
3533 "colorRecovery",(char *) "False");
3534 resource_info->color_recovery=IsMagickTrue(resource_value);
3535 resource_value=XGetResourceClass(database,client_name,"confirmExit",
3537 resource_info->confirm_exit=IsMagickTrue(resource_value);
3538 resource_value=XGetResourceClass(database,client_name,"confirmEdit",
3540 resource_info->confirm_edit=IsMagickTrue(resource_value);
3541 resource_value=XGetResourceClass(database,client_name,"delay",(char *) "1");
3542 resource_info->delay=(unsigned int) StringToUnsignedLong(resource_value);
3543 resource_info->display_gamma=XGetResourceClass(database,client_name,
3544 "displayGamma",(char *) "2.2");
3545 resource_value=XGetResourceClass(database,client_name,"displayWarnings",
3547 resource_info->display_warnings=IsMagickTrue(resource_value);
3548 resource_info->font=XGetResourceClass(database,client_name,"font",
3550 resource_info->font=XGetResourceClass(database,client_name,"fontList",
3551 resource_info->font);
3552 resource_info->font_name[0]=XGetResourceClass(database,client_name,"font1",
3554 resource_info->font_name[1]=XGetResourceClass(database,client_name,"font2",
3555 (char *) "variable");
3556 resource_info->font_name[2]=XGetResourceClass(database,client_name,"font3",
3558 resource_info->font_name[3]=XGetResourceClass(database,client_name,"font4",
3560 resource_info->font_name[4]=XGetResourceClass(database,client_name,"font5",
3561 (char *) "7x13bold");
3562 resource_info->font_name[5]=XGetResourceClass(database,client_name,"font6",
3563 (char *) "8x13bold");
3564 resource_info->font_name[6]=XGetResourceClass(database,client_name,"font7",
3565 (char *) "9x15bold");
3566 resource_info->font_name[7]=XGetResourceClass(database,client_name,"font8",
3568 resource_info->font_name[8]=XGetResourceClass(database,client_name,"font9",
3570 resource_info->font_name[9]=XGetResourceClass(database,client_name,"font0",
3572 resource_info->font_name[10]=XGetResourceClass(database,client_name,"font0",
3574 resource_info->foreground_color=XGetResourceInstance(database,client_name,
3575 "foreground",ForegroundColor);
3576 resource_value=XGetResourceClass(database,client_name,"gammaCorrect",
3578 resource_info->gamma_correct=IsMagickTrue(resource_value);
3579 resource_info->image_geometry=ConstantString(XGetResourceClass(database,
3580 client_name,"geometry",(char *) NULL));
3581 resource_value=XGetResourceClass(database,client_name,"gravity",
3583 resource_info->gravity=(GravityType) ParseCommandOption(MagickGravityOptions,
3584 MagickFalse,resource_value);
3585 directory=getcwd(resource_info->home_directory,MaxTextExtent);
3587 resource_info->icon_geometry=XGetResourceClass(database,client_name,
3588 "iconGeometry",(char *) NULL);
3589 resource_value=XGetResourceClass(database,client_name,"iconic",
3591 resource_info->iconic=IsMagickTrue(resource_value);
3592 resource_value=XGetResourceClass(database,client_name,"immutable",
3593 LocaleCompare(client_name,"PerlMagick") == 0 ? (char *) "True" :
3595 resource_info->immutable=IsMagickTrue(resource_value);
3596 resource_value=XGetResourceClass(database,client_name,"magnify",
3598 resource_info->magnify=(unsigned int) StringToUnsignedLong(resource_value);
3599 resource_info->map_type=XGetResourceClass(database,client_name,"map",
3601 resource_info->matte_color=XGetResourceInstance(database,client_name,
3602 "mattecolor",(char *) NULL);
3603 resource_info->name=ConstantString(XGetResourceClass(database,client_name,
3604 "name",(char *) NULL));
3605 resource_info->pen_colors[0]=XGetResourceClass(database,client_name,"pen1",
3607 resource_info->pen_colors[1]=XGetResourceClass(database,client_name,"pen2",
3609 resource_info->pen_colors[2]=XGetResourceClass(database,client_name,"pen3",
3611 resource_info->pen_colors[3]=XGetResourceClass(database,client_name,"pen4",
3613 resource_info->pen_colors[4]=XGetResourceClass(database,client_name,"pen5",
3615 resource_info->pen_colors[5]=XGetResourceClass(database,client_name,"pen6",
3617 resource_info->pen_colors[6]=XGetResourceClass(database,client_name,"pen7",
3618 (char *) "magenta");
3619 resource_info->pen_colors[7]=XGetResourceClass(database,client_name,"pen8",
3621 resource_info->pen_colors[8]=XGetResourceClass(database,client_name,"pen9",
3623 resource_info->pen_colors[9]=XGetResourceClass(database,client_name,"pen0",
3625 resource_info->pen_colors[10]=XGetResourceClass(database,client_name,"pen0",
3627 resource_value=XGetResourceClass(database,client_name,"pause",(char *) "0");
3628 resource_info->pause=(unsigned int) StringToUnsignedLong(resource_value);
3629 resource_value=XGetResourceClass(database,client_name,"quantum",(char *) "1");
3630 resource_info->quantum=StringToLong(resource_value);
3631 resource_info->text_font=XGetResourceClass(database,client_name,(char *)
3632 "font",(char *) "fixed");
3633 resource_info->text_font=XGetResourceClass(database,client_name,
3634 "textFontList",resource_info->text_font);
3635 resource_info->title=XGetResourceClass(database,client_name,"title",
3637 resource_value=XGetResourceClass(database,client_name,"undoCache",
3639 resource_info->undo_cache=(unsigned int) StringToUnsignedLong(resource_value);
3640 resource_value=XGetResourceClass(database,client_name,"update",
3642 resource_info->update=IsMagickTrue(resource_value);
3643 resource_value=XGetResourceClass(database,client_name,"usePixmap",
3645 resource_info->use_pixmap=IsMagickTrue(resource_value);
3646 resource_value=XGetResourceClass(database,client_name,"sharedMemory",
3648 resource_info->use_shared_memory=IsMagickTrue(resource_value);
3649 resource_info->visual_type=XGetResourceClass(database,client_name,"visual",
3651 resource_info->window_group=XGetResourceClass(database,client_name,
3652 "windowGroup",(char *) NULL);
3653 resource_info->window_id=XGetResourceClass(database,client_name,"window",
3655 resource_info->write_filename=XGetResourceClass(database,client_name,
3656 "writeFilename",(char *) NULL);
3660 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3664 % X G e t R e s o u r c e I n s t a n c e %
3668 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3670 % XGetResourceInstance() queries the X server for the specified resource name.
3671 % If the resource name is not defined in the database, the supplied default
3672 % value is returned.
3674 % The format of the XGetResourceInstance method is:
3676 % char *XGetResourceInstance(XrmDatabase database,const char *client_name,
3677 % const char *keyword,const char *resource_default)
3679 % A description of each parameter follows:
3681 % o database: Specifies a resource database; returned from
3682 % XrmGetStringDatabase.
3684 % o client_name: Specifies the application name used to retrieve
3685 % resource info from the X server database.
3687 % o keyword: Specifies the keyword of the value being retrieved.
3689 % o resource_default: Specifies the default value to return if the query
3690 % fails to find the specified keyword/class.
3693 MagickExport char *XGetResourceInstance(XrmDatabase database,
3694 const char *client_name,const char *keyword,const char *resource_default)
3698 resource_name[MaxTextExtent];
3706 if (database == (XrmDatabase) NULL)
3707 return((char *) resource_default);
3708 *resource_name='\0';
3709 if (keyword != (char *) NULL)
3710 (void) FormatLocaleString(resource_name,MaxTextExtent,"%s.%s",client_name,
3712 status=XrmGetResource(database,resource_name,"ImageMagick",&resource_type,
3714 if (status == False)
3715 return((char *) resource_default);
3716 return(resource_value.addr);
3720 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3724 % X G e t S c r e e n D e n s i t y %
3728 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3730 % XGetScreenDensity() returns the density of the X server screen in
3733 % The format of the XGetScreenDensity method is:
3735 % char *XGetScreenDensity(Display *display)
3737 % A description of each parameter follows:
3739 % o density: XGetScreenDensity() returns the density of the X screen in
3742 % o display: Specifies a connection to an X server; returned from
3746 MagickExport char *XGetScreenDensity(Display *display)
3749 density[MaxTextExtent];
3756 Set density as determined by screen size.
3758 x_density=((((double) DisplayWidth(display,XDefaultScreen(display)))*25.4)/
3759 ((double) DisplayWidthMM(display,XDefaultScreen(display))));
3760 y_density=((((double) DisplayHeight(display,XDefaultScreen(display)))*25.4)/
3761 ((double) DisplayHeightMM(display,XDefaultScreen(display))));
3762 (void) FormatLocaleString(density,MaxTextExtent,"%gx%g",x_density,
3764 return(GetPageGeometry(density));
3768 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3772 + X G e t S u b w i n d o w %
3776 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3778 % XGetSubwindow() returns the subwindow of a window chosen the user with the
3779 % pointer and a button press.
3781 % The format of the XGetSubwindow method is:
3783 % Window XGetSubwindow(Display *display,Window window,int x,int y)
3785 % A description of each parameter follows:
3787 % o subwindow: XGetSubwindow() returns NULL if no subwindow is found
3788 % otherwise the subwindow is returned.
3790 % o display: Specifies a connection to an X server; returned from
3793 % o window: Specifies a pointer to a Window.
3795 % o x: the x coordinate of the pointer relative to the origin of the
3798 % o y: the y coordinate of the pointer relative to the origin of the
3802 static Window XGetSubwindow(Display *display,Window window,int x,int y)
3815 assert(display != (Display *) NULL);
3816 source_window=XRootWindow(display,XDefaultScreen(display));
3817 if (window == (Window) NULL)
3818 return(source_window);
3819 target_window=window;
3822 status=XTranslateCoordinates(display,source_window,window,x,y,
3823 &x_offset,&y_offset,&target_window);
3826 if (target_window == (Window) NULL)
3828 source_window=window;
3829 window=target_window;
3833 if (target_window == (Window) NULL)
3834 target_window=window;
3835 return(target_window);
3839 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3843 % X G e t W i n d o w C o l o r %
3847 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3849 % XGetWindowColor() returns the color of a pixel interactively chosen from the
3852 % The format of the XGetWindowColor method is:
3854 % MagickBooleanType XGetWindowColor(Display *display,XWindows *windows,
3855 % char *name,ExceptionInfo *exception)
3857 % A description of each parameter follows:
3859 % o display: Specifies a connection to an X server; returned from
3862 % o windows: Specifies a pointer to a XWindows structure.
3864 % o name: the name of the color if found in the X Color Database is
3865 % returned in this character string.
3867 % o exception: return any errors or warnings in this structure.
3870 MagickPrivate MagickBooleanType XGetWindowColor(Display *display,
3871 XWindows *windows,char *name,ExceptionInfo *exception)
3902 Choose a pixel from the X server.
3904 assert(display != (Display *) NULL);
3905 assert(name != (char *) NULL);
3906 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",name);
3908 target_window=XSelectWindow(display,&crop_info);
3909 if (target_window == (Window) NULL)
3910 return(MagickFalse);
3911 root_window=XRootWindow(display,XDefaultScreen(display));
3912 client_window=target_window;
3913 if (target_window != root_window)
3921 status=XGetGeometry(display,target_window,&root_window,&x,&x,&d,&d,&d,&d);
3922 if (status != False)
3924 client_window=XClientWindow(display,target_window);
3925 target_window=client_window;
3929 Verify window is viewable.
3931 status=XGetWindowAttributes(display,target_window,&window_attributes);
3932 if ((status == False) || (window_attributes.map_state != IsViewable))
3933 return(MagickFalse);
3937 (void) XTranslateCoordinates(display,root_window,target_window,
3938 (int) crop_info.x,(int) crop_info.y,&x,&y,&child);
3939 ximage=XGetImage(display,target_window,x,y,1,1,AllPlanes,ZPixmap);
3940 if (ximage == (XImage *) NULL)
3941 return(MagickFalse);
3942 color.pixel=XGetPixel(ximage,0,0);
3943 XDestroyImage(ximage);
3945 Match color against the color database.
3947 (void) XQueryColor(display,window_attributes.colormap,&color);
3948 pixel.red=(double) ScaleShortToQuantum(color.red);
3949 pixel.green=(double) ScaleShortToQuantum(color.green);
3950 pixel.blue=(double) ScaleShortToQuantum(color.blue);
3951 pixel.alpha=OpaqueAlpha;
3952 (void) QueryColorname(windows->image.image,&pixel,X11Compliance,name,
3958 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3962 + X G e t W i n d o w I m a g e %
3966 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3968 % XGetWindowImage() reads an image from the target X window and returns it.
3969 % XGetWindowImage() optionally descends the window hierarchy and overlays the
3970 % target image with each child image in an optimized fashion. Any child
3971 % window that have the same visual, colormap, and are contained by its parent
3974 % The format of the XGetWindowImage method is:
3976 % Image *XGetWindowImage(Display *display,const Window window,
3977 % const unsigned int borders,const unsigned int level,
3978 % ExceptionInfo *exception)
3980 % A description of each parameter follows:
3982 % o display: Specifies a connection to an X server; returned from
3985 % o window: Specifies the window to obtain the image from.
3987 % o borders: Specifies whether borders pixels are to be saved with
3990 % o level: Specifies an unsigned integer representing the level of
3991 % decent in the window hierarchy. This value must be zero or one on
3992 % the initial call to XGetWindowImage. A value of zero returns after
3993 % one call. A value of one causes the function to descend the window
3994 % hierarchy and overlay the target image with each subwindow image.
3996 % o exception: return any errors or warnings in this structure.
3999 static Image *XGetWindowImage(Display *display,const Window window,
4000 const unsigned int borders,const unsigned int level,ExceptionInfo *exception)
4002 typedef struct _ColormapInfo
4010 struct _ColormapInfo
4014 typedef struct _WindowInfo
4050 *colormap_info = (ColormapInfo *) NULL;
4070 Verify window is viewable.
4072 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
4073 assert(display != (Display *) NULL);
4074 status=XGetWindowAttributes(display,window,&window_attributes);
4075 if ((status == False) || (window_attributes.map_state != IsViewable))
4076 return((Image *) NULL);
4078 Cropping rectangle is relative to root window.
4080 root_window=XRootWindow(display,XDefaultScreen(display));
4081 (void) XTranslateCoordinates(display,window,root_window,0,0,&x_offset,
4083 crop_info.x=(ssize_t) x_offset;
4084 crop_info.y=(ssize_t) y_offset;
4085 crop_info.width=(size_t) window_attributes.width;
4086 crop_info.height=(size_t) window_attributes.height;
4087 if (borders != MagickFalse)
4090 Include border in image.
4092 crop_info.x-=(ssize_t) window_attributes.border_width;
4093 crop_info.y-=(ssize_t) window_attributes.border_width;
4094 crop_info.width+=(size_t) (window_attributes.border_width << 1);
4095 crop_info.height+=(size_t) (window_attributes.border_width << 1);
4098 Crop to root window.
4100 if (crop_info.x < 0)
4102 crop_info.width+=crop_info.x;
4105 if (crop_info.y < 0)
4107 crop_info.height+=crop_info.y;
4110 display_width=XDisplayWidth(display,XDefaultScreen(display));
4111 if ((int) (crop_info.x+crop_info.width) > display_width)
4112 crop_info.width=(size_t) (display_width-crop_info.x);
4113 display_height=XDisplayHeight(display,XDefaultScreen(display));
4114 if ((int) (crop_info.y+crop_info.height) > display_height)
4115 crop_info.height=(size_t) (display_height-crop_info.y);
4117 Initialize window info attributes.
4119 if (number_windows >= max_windows)
4122 Allocate or resize window info buffer.
4125 if (window_info == (WindowInfo *) NULL)
4126 window_info=(WindowInfo *) AcquireQuantumMemory((size_t) max_windows,
4127 sizeof(*window_info));
4129 window_info=(WindowInfo *) ResizeQuantumMemory(window_info,(size_t)
4130 max_windows,sizeof(*window_info));
4132 if (window_info == (WindowInfo *) NULL)
4134 ThrowXWindowFatalException(ResourceLimitError,
4135 "MemoryAllocationFailed","...");
4136 return((Image *) NULL);
4138 id=number_windows++;
4139 window_info[id].window=window;
4140 window_info[id].visual=window_attributes.visual;
4141 window_info[id].colormap=window_attributes.colormap;
4142 window_info[id].bounds.x1=(short) crop_info.x;
4143 window_info[id].bounds.y1=(short) crop_info.y;
4144 window_info[id].bounds.x2=(short) (crop_info.x+(int) crop_info.width-1);
4145 window_info[id].bounds.y2=(short) (crop_info.y+(int) crop_info.height-1);
4146 crop_info.x-=x_offset;
4147 crop_info.y-=y_offset;
4148 window_info[id].crop_info=crop_info;
4158 Descend the window hierarchy.
4160 status=XQueryTree(display,window,&root_window,&window_info[id].parent,
4161 &children,&number_children);
4162 for (i=0; i < id; i++)
4163 if ((window_info[i].window == window_info[id].parent) &&
4164 (window_info[i].visual == window_info[id].visual) &&
4165 (window_info[i].colormap == window_info[id].colormap))
4167 if ((window_info[id].bounds.x1 <= window_info[i].bounds.x1) ||
4168 (window_info[id].bounds.x1 >= window_info[i].bounds.x2) ||
4169 (window_info[id].bounds.y1 <= window_info[i].bounds.y1) ||
4170 (window_info[id].bounds.y1 >= window_info[i].bounds.y2))
4173 Eliminate windows not circumscribed by their parent.
4179 if ((status == True) && (number_children != 0))
4181 for (i=0; i < (int) number_children; i++)
4182 (void) XGetWindowImage(display,children[i],MagickFalse,level+1,
4184 (void) XFree((void *) children);
4225 Get X image for each window in the list.
4227 image=NewImageList();
4228 for (id=0; id < number_windows; id++)
4231 Does target window intersect top level window?
4234 ((window_info[id].bounds.x2 >= window_info[0].bounds.x1) &&
4235 (window_info[id].bounds.x1 <= window_info[0].bounds.x2) &&
4236 (window_info[id].bounds.y2 >= window_info[0].bounds.y1) &&
4237 (window_info[id].bounds.y1 <= window_info[0].bounds.y2)) ?
4238 MagickTrue : MagickFalse;
4240 Is target window contained by another window with the same colormap?
4242 for (j=0; j < id; j++)
4243 if ((window_info[id].visual == window_info[j].visual) &&
4244 (window_info[id].colormap == window_info[j].colormap))
4246 if ((window_info[id].bounds.x1 <= window_info[j].bounds.x1) ||
4247 (window_info[id].bounds.x1 >= window_info[j].bounds.x2) ||
4248 (window_info[id].bounds.y1 <= window_info[j].bounds.y1) ||
4249 (window_info[id].bounds.y1 >= window_info[j].bounds.y2))
4253 if ((window_info[id].visual != window_info[j].visual) ||
4254 (window_info[id].colormap != window_info[j].colormap))
4256 if ((window_info[id].bounds.x2 > window_info[j].bounds.x1) &&
4257 (window_info[id].bounds.x1 < window_info[j].bounds.x2) &&
4258 (window_info[id].bounds.y2 > window_info[j].bounds.y1) &&
4259 (window_info[id].bounds.y1 < window_info[j].bounds.y2))
4262 if (import == MagickFalse)
4267 ximage=XGetImage(display,window_info[id].window,(int)
4268 window_info[id].crop_info.x,(int) window_info[id].crop_info.y,
4269 (unsigned int) window_info[id].crop_info.width,(unsigned int)
4270 window_info[id].crop_info.height,AllPlanes,ZPixmap);
4271 if (ximage == (XImage *) NULL)
4274 Initialize window colormap.
4277 colors=(XColor *) NULL;
4278 if (window_info[id].colormap != (Colormap) NULL)
4284 Search colormap list for window colormap.
4286 number_colors=(unsigned int) window_info[id].visual->map_entries;
4287 for (p=colormap_info; p != (ColormapInfo *) NULL; p=p->next)
4288 if (p->colormap == window_info[id].colormap)
4290 if (p == (ColormapInfo *) NULL)
4293 Get the window colormap.
4295 colors=(XColor *) AcquireQuantumMemory(number_colors,
4297 if (colors == (XColor *) NULL)
4299 XDestroyImage(ximage);
4300 return((Image *) NULL);
4302 if ((window_info[id].visual->klass != DirectColor) &&
4303 (window_info[id].visual->klass != TrueColor))
4304 for (i=0; i < (int) number_colors; i++)
4306 colors[i].pixel=(size_t) i;
4320 DirectColor or TrueColor visual.
4325 red_bit=window_info[id].visual->red_mask &
4326 (~(window_info[id].visual->red_mask)+1);
4327 green_bit=window_info[id].visual->green_mask &
4328 (~(window_info[id].visual->green_mask)+1);
4329 blue_bit=window_info[id].visual->blue_mask &
4330 (~(window_info[id].visual->blue_mask)+1);
4331 for (i=0; i < (int) number_colors; i++)
4333 colors[i].pixel=(unsigned long) (red | green | blue);
4336 if (red > window_info[id].visual->red_mask)
4339 if (green > window_info[id].visual->green_mask)
4342 if (blue > window_info[id].visual->blue_mask)
4346 (void) XQueryColors(display,window_info[id].colormap,colors,
4347 (int) number_colors);
4349 Append colormap to colormap list.
4351 p=(ColormapInfo *) AcquireMagickMemory(sizeof(*p));
4352 if (p == (ColormapInfo *) NULL)
4353 return((Image *) NULL);
4354 p->colormap=window_info[id].colormap;
4356 p->next=colormap_info;
4362 Allocate image structure.
4364 composite_image=AcquireImage((ImageInfo *) NULL,exception);
4365 if (composite_image == (Image *) NULL)
4367 XDestroyImage(ximage);
4368 return((Image *) NULL);
4371 Convert X image to MIFF format.
4373 if ((window_info[id].visual->klass != TrueColor) &&
4374 (window_info[id].visual->klass != DirectColor))
4375 composite_image->storage_class=PseudoClass;
4376 composite_image->columns=(size_t) ximage->width;
4377 composite_image->rows=(size_t) ximage->height;
4378 composite_view=AcquireCacheView(composite_image);
4379 switch (composite_image->storage_class)
4397 Determine shift and mask for red, green, and blue.
4399 red_mask=window_info[id].visual->red_mask;
4401 while ((red_mask != 0) && ((red_mask & 0x01) == 0))
4406 green_mask=window_info[id].visual->green_mask;
4408 while ((green_mask != 0) && ((green_mask & 0x01) == 0))
4413 blue_mask=window_info[id].visual->blue_mask;
4415 while ((blue_mask != 0) && ((blue_mask & 0x01) == 0))
4421 Convert X image to DirectClass packets.
4423 if ((number_colors != 0) &&
4424 (window_info[id].visual->klass == DirectColor))
4425 for (y=0; y < (int) composite_image->rows; y++)
4427 q=QueueCacheViewAuthenticPixels(composite_view,0,(ssize_t) y,
4428 composite_image->columns,1,exception);
4429 if (q == (Quantum *) NULL)
4431 for (x=0; x < (int) composite_image->columns; x++)
4433 pixel=XGetPixel(ximage,x,y);
4434 index=(pixel >> red_shift) & red_mask;
4435 SetPixelRed(composite_image,
4436 ScaleShortToQuantum(colors[index].red),q);
4437 index=(pixel >> green_shift) & green_mask;
4438 SetPixelGreen(composite_image,
4439 ScaleShortToQuantum(colors[index].green),q);
4440 index=(pixel >> blue_shift) & blue_mask;
4441 SetPixelBlue(composite_image,
4442 ScaleShortToQuantum(colors[index].blue),q);
4443 q+=GetPixelChannels(composite_image);
4445 status=SyncCacheViewAuthenticPixels(composite_view,exception);
4446 if (status == MagickFalse)
4450 for (y=0; y < (int) composite_image->rows; y++)
4452 q=QueueCacheViewAuthenticPixels(composite_view,0,(ssize_t) y,
4453 composite_image->columns,1,exception);
4454 if (q == (Quantum *) NULL)
4456 for (x=0; x < (int) composite_image->columns; x++)
4458 pixel=XGetPixel(ximage,x,y);
4459 color=(pixel >> red_shift) & red_mask;
4460 color=(65535UL*color)/red_mask;
4461 SetPixelRed(composite_image,
4462 ScaleShortToQuantum((unsigned short) color),q);
4463 color=(pixel >> green_shift) & green_mask;
4464 color=(65535UL*color)/green_mask;
4465 SetPixelGreen(composite_image,
4466 ScaleShortToQuantum((unsigned short) color),q);
4467 color=(pixel >> blue_shift) & blue_mask;
4468 color=(65535UL*color)/blue_mask;
4469 SetPixelBlue(composite_image,
4470 ScaleShortToQuantum((unsigned short) color),q);
4471 q+=GetPixelChannels(composite_image);
4473 status=SyncCacheViewAuthenticPixels(composite_view,exception);
4474 if (status == MagickFalse)
4484 status=AcquireImageColormap(composite_image,number_colors,
4486 if (status == MagickFalse)
4488 XDestroyImage(ximage);
4489 composite_image=DestroyImage(composite_image);
4490 return((Image *) NULL);
4492 for (i=0; i < (int) composite_image->colors; i++)
4494 composite_image->colormap[colors[i].pixel].red=(double)
4495 ScaleShortToQuantum(colors[i].red);
4496 composite_image->colormap[colors[i].pixel].green=(double)
4497 ScaleShortToQuantum(colors[i].green);
4498 composite_image->colormap[colors[i].pixel].blue=(double)
4499 ScaleShortToQuantum(colors[i].blue);
4502 Convert X image to PseudoClass packets.
4504 for (y=0; y < (int) composite_image->rows; y++)
4506 q=QueueCacheViewAuthenticPixels(composite_view,0,(ssize_t) y,
4507 composite_image->columns,1,exception);
4508 if (q == (Quantum *) NULL)
4510 for (x=0; x < (int) composite_image->columns; x++)
4512 index=(Quantum) XGetPixel(ximage,x,y);
4513 SetPixelIndex(composite_image,index,q);
4514 SetPixelInfoPixel(composite_image,
4515 composite_image->colormap+(ssize_t) index,q);
4516 q+=GetPixelChannels(composite_image);
4518 status=SyncCacheViewAuthenticPixels(composite_view,exception);
4519 if (status == MagickFalse)
4525 composite_view=DestroyCacheView(composite_view);
4526 XDestroyImage(ximage);
4527 if (image == (Image *) NULL)
4529 image=composite_image;
4533 Composite any children in back-to-front order.
4535 (void) XTranslateCoordinates(display,window_info[id].window,window,0,0,
4536 &x_offset,&y_offset,&child);
4537 x_offset-=(int) crop_info.x;
4540 y_offset-=(int) crop_info.y;
4543 (void) CompositeImage(image,CopyCompositeOp,composite_image,(ssize_t)
4544 x_offset,(ssize_t) y_offset,exception);
4547 Relinquish resources.
4549 while (colormap_info != (ColormapInfo *) NULL)
4551 next=colormap_info->next;
4552 colormap_info->colors=(XColor *) RelinquishMagickMemory(
4553 colormap_info->colors);
4554 colormap_info=(ColormapInfo *) RelinquishMagickMemory(colormap_info);
4558 Relinquish resources and restore initial state.
4560 window_info=(WindowInfo *) RelinquishMagickMemory(window_info);
4563 colormap_info=(ColormapInfo *) NULL;
4566 return((Image *) NULL);
4570 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
4574 % X G e t W i n d o w I n f o %
4578 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
4580 % XGetWindowInfo() initializes the XWindowInfo structure.
4582 % The format of the XGetWindowInfo method is:
4584 % void XGetWindowInfo(Display *display,XVisualInfo *visual_info,
4585 % XStandardColormap *map_info,XPixelInfo *pixel,XFontStruct *font_info,
4586 % XResourceInfo *resource_info,XWindowInfo *window)
4587 % resource_info,window)
4589 % A description of each parameter follows:
4591 % o display: Specifies a connection to an X server; returned from
4594 % o visual_info: Specifies a pointer to a X11 XVisualInfo structure;
4595 % returned from XGetVisualInfo.
4597 % o map_info: If map_type is specified, this structure is initialized
4598 % with info from the Standard Colormap.
4600 % o pixel: Specifies a pointer to a XPixelInfo structure.
4602 % o font_info: Specifies a pointer to a XFontStruct structure.
4604 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
4607 MagickPrivate void XGetWindowInfo(Display *display,XVisualInfo *visual_info,
4608 XStandardColormap *map_info,XPixelInfo *pixel,XFontStruct *font_info,
4609 XResourceInfo *resource_info,XWindowInfo *window)
4612 Initialize window info.
4614 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
4615 assert(display != (Display *) NULL);
4616 assert(visual_info != (XVisualInfo *) NULL);
4617 assert(map_info != (XStandardColormap *) NULL);
4618 assert(pixel != (XPixelInfo *) NULL);
4619 assert(resource_info != (XResourceInfo *) NULL);
4620 assert(window != (XWindowInfo *) NULL);
4621 if (window->id != (Window) NULL)
4623 if (window->cursor != (Cursor) NULL)
4624 (void) XFreeCursor(display,window->cursor);
4625 if (window->busy_cursor != (Cursor) NULL)
4626 (void) XFreeCursor(display,window->busy_cursor);
4627 if (window->highlight_stipple != (Pixmap) NULL)
4628 (void) XFreePixmap(display,window->highlight_stipple);
4629 if (window->shadow_stipple != (Pixmap) NULL)
4630 (void) XFreePixmap(display,window->shadow_stipple);
4631 if (window->name == (char *) NULL)
4632 window->name=AcquireString("");
4633 if (window->icon_name == (char *) NULL)
4634 window->icon_name=AcquireString("");
4639 Initialize these attributes just once.
4641 window->id=(Window) NULL;
4642 if (window->name == (char *) NULL)
4643 window->name=AcquireString("");
4644 if (window->icon_name == (char *) NULL)
4645 window->icon_name=AcquireString("");
4646 window->x=XDisplayWidth(display,visual_info->screen) >> 1;
4647 window->y=XDisplayWidth(display,visual_info->screen) >> 1;
4648 window->ximage=(XImage *) NULL;
4649 window->matte_image=(XImage *) NULL;
4650 window->pixmap=(Pixmap) NULL;
4651 window->matte_pixmap=(Pixmap) NULL;
4652 window->mapped=MagickFalse;
4653 window->stasis=MagickFalse;
4654 window->shared_memory=MagickTrue;
4655 window->segment_info=(void *) NULL;
4656 #if defined(MAGICKCORE_HAVE_SHARED_MEMORY)
4661 if (window->segment_info == (void *) NULL)
4662 window->segment_info=AcquireQuantumMemory(2,sizeof(*segment_info));
4663 segment_info=(XShmSegmentInfo *) window->segment_info;
4664 segment_info[0].shmid=(-1);
4665 segment_info[0].shmaddr=(char *) NULL;
4666 segment_info[1].shmid=(-1);
4667 segment_info[1].shmaddr=(char *) NULL;
4672 Initialize these attributes every time function is called.
4674 window->screen=visual_info->screen;
4675 window->root=XRootWindow(display,visual_info->screen);
4676 window->visual=visual_info->visual;
4677 window->storage_class=(unsigned int) visual_info->klass;
4678 window->depth=(unsigned int) visual_info->depth;
4679 window->visual_info=visual_info;
4680 window->map_info=map_info;
4681 window->pixel_info=pixel;
4682 window->font_info=font_info;
4683 window->cursor=XCreateFontCursor(display,XC_left_ptr);
4684 window->busy_cursor=XCreateFontCursor(display,XC_watch);
4685 window->geometry=(char *) NULL;
4686 window->icon_geometry=(char *) NULL;
4687 if (resource_info->icon_geometry != (char *) NULL)
4688 (void) CloneString(&window->icon_geometry,resource_info->icon_geometry);
4689 window->crop_geometry=(char *) NULL;
4690 window->flags=(size_t) PSize;
4693 window->min_width=1;
4694 window->min_height=1;
4695 window->width_inc=1;
4696 window->height_inc=1;
4697 window->border_width=resource_info->border_width;
4698 window->annotate_context=pixel->annotate_context;
4699 window->highlight_context=pixel->highlight_context;
4700 window->widget_context=pixel->widget_context;
4701 window->shadow_stipple=(Pixmap) NULL;
4702 window->highlight_stipple=(Pixmap) NULL;
4703 window->use_pixmap=MagickTrue;
4704 window->immutable=MagickFalse;
4705 window->shape=MagickFalse;
4707 window->mask=(int) (CWBackingStore | CWBackPixel | CWBackPixmap |
4708 CWBitGravity | CWBorderPixel | CWColormap | CWCursor | CWDontPropagate |
4709 CWEventMask | CWOverrideRedirect | CWSaveUnder | CWWinGravity);
4710 window->attributes.background_pixel=pixel->background_color.pixel;
4711 window->attributes.background_pixmap=(Pixmap) NULL;
4712 window->attributes.bit_gravity=ForgetGravity;
4713 window->attributes.backing_store=WhenMapped;
4714 window->attributes.save_under=MagickTrue;
4715 window->attributes.border_pixel=pixel->border_color.pixel;
4716 window->attributes.colormap=map_info->colormap;
4717 window->attributes.cursor=window->cursor;
4718 window->attributes.do_not_propagate_mask=NoEventMask;
4719 window->attributes.event_mask=NoEventMask;
4720 window->attributes.override_redirect=MagickFalse;
4721 window->attributes.win_gravity=NorthWestGravity;
4722 window->orphan=MagickFalse;
4726 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
4730 % X H i g h l i g h t E l l i p s e %
4734 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
4736 % XHighlightEllipse() puts a border on the X server around a region defined by
4739 % The format of the XHighlightEllipse method is:
4741 % void XHighlightEllipse(Display *display,Window window,
4742 % GC annotate_context,const RectangleInfo *highlight_info)
4744 % A description of each parameter follows:
4746 % o display: Specifies a connection to an X server; returned from
4749 % o window: Specifies a pointer to a Window structure.
4751 % o annotate_context: Specifies a pointer to a GC structure.
4753 % o highlight_info: Specifies a pointer to a RectangleInfo structure. It
4754 % contains the extents of any highlighting rectangle.
4757 MagickPrivate void XHighlightEllipse(Display *display,Window window,
4758 GC annotate_context,const RectangleInfo *highlight_info)
4760 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
4761 assert(display != (Display *) NULL);
4762 assert(window != (Window) NULL);
4763 assert(annotate_context != (GC) NULL);
4764 assert(highlight_info != (RectangleInfo *) NULL);
4765 if ((highlight_info->width < 4) || (highlight_info->height < 4))
4767 (void) XDrawArc(display,window,annotate_context,(int) highlight_info->x,
4768 (int) highlight_info->y,(unsigned int) highlight_info->width-1,
4769 (unsigned int) highlight_info->height-1,0,360*64);
4770 (void) XDrawArc(display,window,annotate_context,(int) highlight_info->x+1,
4771 (int) highlight_info->y+1,(unsigned int) highlight_info->width-3,
4772 (unsigned int) highlight_info->height-3,0,360*64);
4776 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
4780 % X H i g h l i g h t L i n e %
4784 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
4786 % XHighlightLine() puts a border on the X server around a region defined by
4789 % The format of the XHighlightLine method is:
4791 % void XHighlightLine(Display *display,Window window,GC annotate_context,
4792 % const XSegment *highlight_info)
4794 % A description of each parameter follows:
4796 % o display: Specifies a connection to an X server; returned from
4799 % o window: Specifies a pointer to a Window structure.
4801 % o annotate_context: Specifies a pointer to a GC structure.
4803 % o highlight_info: Specifies a pointer to a RectangleInfo structure. It
4804 % contains the extents of any highlighting rectangle.
4807 MagickPrivate void XHighlightLine(Display *display,Window window,
4808 GC annotate_context,const XSegment *highlight_info)
4810 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
4811 assert(display != (Display *) NULL);
4812 assert(window != (Window) NULL);
4813 assert(annotate_context != (GC) NULL);
4814 assert(highlight_info != (XSegment *) NULL);
4815 (void) XDrawLine(display,window,annotate_context,highlight_info->x1,
4816 highlight_info->y1,highlight_info->x2,highlight_info->y2);
4820 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
4824 % X H i g h l i g h t R e c t a n g l e %
4828 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
4830 % XHighlightRectangle() puts a border on the X server around a region defined
4831 % by highlight_info.
4833 % The format of the XHighlightRectangle method is:
4835 % void XHighlightRectangle(Display *display,Window window,
4836 % GC annotate_context,const RectangleInfo *highlight_info)
4838 % A description of each parameter follows:
4840 % o display: Specifies a connection to an X server; returned from
4843 % o window: Specifies a pointer to a Window structure.
4845 % o annotate_context: Specifies a pointer to a GC structure.
4847 % o highlight_info: Specifies a pointer to a RectangleInfo structure. It
4848 % contains the extents of any highlighting rectangle.
4851 MagickPrivate void XHighlightRectangle(Display *display,Window window,
4852 GC annotate_context,const RectangleInfo *highlight_info)
4854 assert(display != (Display *) NULL);
4855 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
4856 assert(window != (Window) NULL);
4857 assert(annotate_context != (GC) NULL);
4858 assert(highlight_info != (RectangleInfo *) NULL);
4859 if ((highlight_info->width < 4) || (highlight_info->height < 4))
4861 (void) XDrawRectangle(display,window,annotate_context,(int) highlight_info->x,
4862 (int) highlight_info->y,(unsigned int) highlight_info->width-1,
4863 (unsigned int) highlight_info->height-1);
4864 (void) XDrawRectangle(display,window,annotate_context,(int) highlight_info->x+
4865 1,(int) highlight_info->y+1,(unsigned int) highlight_info->width-3,
4866 (unsigned int) highlight_info->height-3);
4870 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
4874 % X I m p o r t I m a g e %
4878 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
4880 % XImportImage() reads an image from an X window.
4882 % The format of the XImportImage method is:
4884 % Image *XImportImage(const ImageInfo *image_info,XImportInfo *ximage_info,
4885 % ExceptionInfo *exception)
4887 % A description of each parameter follows:
4889 % o image_info: the image info.
4891 % o ximage_info: Specifies a pointer to an XImportInfo structure.
4893 % o exception: return any errors or warnings in this structure.
4896 MagickExport Image *XImportImage(const ImageInfo *image_info,
4897 XImportInfo *ximage_info,ExceptionInfo *exception)
4930 Open X server connection.
4932 assert(image_info != (const ImageInfo *) NULL);
4933 assert(image_info->signature == MagickSignature);
4934 if (image_info->debug != MagickFalse)
4935 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
4936 image_info->filename);
4937 assert(ximage_info != (XImportInfo *) NULL);
4938 display=XOpenDisplay(image_info->server_name);
4939 if (display == (Display *) NULL)
4941 ThrowXWindowFatalException(XServerError,"UnableToOpenXServer",
4942 XDisplayName(image_info->server_name));
4943 return((Image *) NULL);
4946 Set our forgiving exception handler.
4948 (void) XSetErrorHandler(XError);
4950 Select target window.
4956 root=XRootWindow(display,XDefaultScreen(display));
4957 target=(Window) NULL;
4958 if ((image_info->filename != (char *) NULL) &&
4959 (*image_info->filename != '\0'))
4961 if (LocaleCompare(image_info->filename,"root") == 0)
4966 Select window by ID or name.
4968 if (isdigit((unsigned char) *image_info->filename) != 0)
4969 target=XWindowByID(display,root,(Window)
4970 strtol(image_info->filename,(char **) NULL,0));
4971 if (target == (Window) NULL)
4972 target=XWindowByName(display,root,image_info->filename);
4973 if (target == (Window) NULL)
4974 ThrowXWindowFatalException(XServerError,
4975 "NoWindowWithSpecifiedIDExists",image_info->filename);
4979 If target window is not defined, interactively select one.
4981 prior_target=target;
4982 if (target == (Window) NULL)
4983 target=XSelectWindow(display,&crop_info);
4984 if (target == (Window) NULL)
4985 ThrowXWindowFatalException(XServerError,"UnableToReadXWindowImage",
4986 image_info->filename);
4987 client=target; /* obsolete */
4993 status=XGetGeometry(display,target,&root,&x,&x,&d,&d,&d,&d);
4994 if (status != False)
5002 Find window manager frame.
5004 status=XQueryTree(display,target,&root,&parent,&children,&d);
5005 if ((status != False) && (children != (Window *) NULL))
5006 (void) XFree((char *) children);
5007 if ((status == False) || (parent == (Window) NULL) ||
5015 client=XClientWindow(display,target);
5016 if (ximage_info->frame == MagickFalse)
5018 if ((ximage_info->frame == MagickFalse) &&
5019 (prior_target != MagickFalse))
5020 target=prior_target;
5023 if (ximage_info->screen)
5035 Obtain window image directly from screen.
5037 status=XGetWindowAttributes(display,target,&window_attributes);
5038 if (status == False)
5040 ThrowXWindowFatalException(XServerError,
5041 "UnableToReadXWindowAttributes",image_info->filename);
5042 (void) XCloseDisplay(display);
5043 return((Image *) NULL);
5045 (void) XTranslateCoordinates(display,target,root,0,0,&x,&y,&child);
5046 crop_info.x=(ssize_t) x;
5047 crop_info.y=(ssize_t) y;
5048 crop_info.width=(size_t) window_attributes.width;
5049 crop_info.height=(size_t) window_attributes.height;
5050 if (ximage_info->borders != 0)
5053 Include border in image.
5055 crop_info.x-=window_attributes.border_width;
5056 crop_info.y-=window_attributes.border_width;
5057 crop_info.width+=window_attributes.border_width << 1;
5058 crop_info.height+=window_attributes.border_width << 1;
5063 If WM_COLORMAP_WINDOWS property is set or multiple colormaps, descend.
5066 status=XGetWMColormapWindows(display,target,&children,&number_windows);
5067 if ((status == True) && (number_windows > 0))
5069 ximage_info->descend=MagickTrue;
5070 (void) XFree ((char *) children);
5072 colormaps=XListInstalledColormaps(display,target,&number_colormaps);
5073 if (number_colormaps > 0)
5075 if (number_colormaps > 1)
5076 ximage_info->descend=MagickTrue;
5077 (void) XFree((char *) colormaps);
5080 Alert the user not to alter the screen.
5082 if (ximage_info->silent == MagickFalse)
5083 (void) XBell(display,0);
5085 Get image by window id.
5087 (void) XGrabServer(display);
5088 image=XGetWindowImage(display,target,ximage_info->borders,
5089 ximage_info->descend ? 1U : 0U,exception);
5090 (void) XUngrabServer(display);
5091 if (image == (Image *) NULL)
5092 ThrowXWindowFatalException(XServerError,"UnableToReadXWindowImage",
5093 image_info->filename)
5096 (void) CopyMagickString(image->filename,image_info->filename,
5098 if ((crop_info.width != 0) && (crop_info.height != 0))
5105 Crop image as defined by the cropping rectangle.
5107 clone_image=CloneImage(image,0,0,MagickTrue,exception);
5108 if (clone_image != (Image *) NULL)
5110 crop_image=CropImage(clone_image,&crop_info,exception);
5111 if (crop_image != (Image *) NULL)
5113 image=DestroyImage(image);
5118 status=XGetWMName(display,target,&window_name);
5121 if ((image_info->filename != (char *) NULL) &&
5122 (*image_info->filename == '\0'))
5123 (void) CopyMagickString(image->filename,(char *) window_name.value,
5124 (size_t) window_name.nitems+1);
5125 (void) XFree((void *) window_name.value);
5128 if (ximage_info->silent == MagickFalse)
5131 Alert the user we're done.
5133 (void) XBell(display,0);
5134 (void) XBell(display,0);
5136 (void) XCloseDisplay(display);
5141 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
5145 % X I n i t i a l i z e W i n d o w s %
5149 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
5151 % XInitializeWindows() initializes the XWindows structure.
5153 % The format of the XInitializeWindows method is:
5155 % XWindows *XInitializeWindows(Display *display,
5156 % XResourceInfo *resource_info)
5158 % A description of each parameter follows:
5160 % o windows: XInitializeWindows returns a pointer to a XWindows structure.
5162 % o display: Specifies a connection to an X server; returned from
5165 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
5168 MagickPrivate XWindows *XInitializeWindows(Display *display,
5169 XResourceInfo *resource_info)
5178 Allocate windows structure.
5180 windows=(XWindows *) AcquireMagickMemory(sizeof(*windows));
5181 if (windows == (XWindows *) NULL)
5183 ThrowXWindowFatalException(XServerFatalError,"MemoryAllocationFailed",
5185 return((XWindows *) NULL);
5187 (void) ResetMagickMemory(windows,0,sizeof(*windows));
5188 windows->pixel_info=(XPixelInfo *) AcquireMagickMemory(
5189 sizeof(*windows->pixel_info));
5190 windows->icon_pixel=(XPixelInfo *) AcquireMagickMemory(
5191 sizeof(*windows->icon_pixel));
5192 windows->icon_resources=(XResourceInfo *) AcquireMagickMemory(
5193 sizeof(*windows->icon_resources));
5194 if ((windows->pixel_info == (XPixelInfo *) NULL) ||
5195 (windows->icon_pixel == (XPixelInfo *) NULL) ||
5196 (windows->icon_resources == (XResourceInfo *) NULL))
5198 ThrowXWindowFatalException(XServerFatalError,"MemoryAllocationFailed",
5200 return((XWindows *) NULL);
5203 Initialize windows structure.
5205 windows->display=display;
5206 windows->wm_protocols=XInternAtom(display,"WM_PROTOCOLS",MagickFalse);
5207 windows->wm_delete_window=XInternAtom(display,"WM_DELETE_WINDOW",MagickFalse);
5208 windows->wm_take_focus=XInternAtom(display,"WM_TAKE_FOCUS",MagickFalse);
5209 windows->im_protocols=XInternAtom(display,"IM_PROTOCOLS",MagickFalse);
5210 windows->im_remote_command=
5211 XInternAtom(display,"IM_REMOTE_COMMAND",MagickFalse);
5212 windows->im_update_widget=XInternAtom(display,"IM_UPDATE_WIDGET",MagickFalse);
5213 windows->im_update_colormap=
5214 XInternAtom(display,"IM_UPDATE_COLORMAP",MagickFalse);
5215 windows->im_former_image=XInternAtom(display,"IM_FORMER_IMAGE",MagickFalse);
5216 windows->im_next_image=XInternAtom(display,"IM_NEXT_IMAGE",MagickFalse);
5217 windows->im_retain_colors=XInternAtom(display,"IM_RETAIN_COLORS",MagickFalse);
5218 windows->im_exit=XInternAtom(display,"IM_EXIT",MagickFalse);
5219 windows->dnd_protocols=XInternAtom(display,"DndProtocol",MagickFalse);
5220 #if defined(MAGICKCORE_WINDOWS_SUPPORT)
5221 (void) XSynchronize(display,IsWindows95());
5223 if (IsEventLogging())
5225 (void) XSynchronize(display,MagickTrue);
5226 (void) LogMagickEvent(X11Event,GetMagickModule(),"Version: %s",
5227 GetMagickVersion((size_t *) NULL));
5228 (void) LogMagickEvent(X11Event,GetMagickModule(),"Protocols:");
5229 (void) LogMagickEvent(X11Event,GetMagickModule(),
5230 " Window Manager: 0x%lx",windows->wm_protocols);
5231 (void) LogMagickEvent(X11Event,GetMagickModule(),
5232 " delete window: 0x%lx",windows->wm_delete_window);
5233 (void) LogMagickEvent(X11Event,GetMagickModule()," take focus: 0x%lx",
5234 windows->wm_take_focus);
5235 (void) LogMagickEvent(X11Event,GetMagickModule()," ImageMagick: 0x%lx",
5236 windows->im_protocols);
5237 (void) LogMagickEvent(X11Event,GetMagickModule(),
5238 " remote command: 0x%lx",windows->im_remote_command);
5239 (void) LogMagickEvent(X11Event,GetMagickModule(),
5240 " update widget: 0x%lx",windows->im_update_widget);
5241 (void) LogMagickEvent(X11Event,GetMagickModule(),
5242 " update colormap: 0x%lx",windows->im_update_colormap);
5243 (void) LogMagickEvent(X11Event,GetMagickModule(),
5244 " former image: 0x%lx",windows->im_former_image);
5245 (void) LogMagickEvent(X11Event,GetMagickModule()," next image: 0x%lx",
5246 windows->im_next_image);
5247 (void) LogMagickEvent(X11Event,GetMagickModule(),
5248 " retain colors: 0x%lx",windows->im_retain_colors);
5249 (void) LogMagickEvent(X11Event,GetMagickModule()," exit: 0x%lx",
5251 (void) LogMagickEvent(X11Event,GetMagickModule()," Drag and Drop: 0x%lx",
5252 windows->dnd_protocols);
5255 Allocate standard colormap.
5257 windows->map_info=XAllocStandardColormap();
5258 windows->icon_map=XAllocStandardColormap();
5259 if ((windows->map_info == (XStandardColormap *) NULL) ||
5260 (windows->icon_map == (XStandardColormap *) NULL))
5261 ThrowXWindowFatalException(ResourceLimitFatalError,
5262 "MemoryAllocationFailed","...");
5263 windows->map_info->colormap=(Colormap) NULL;
5264 windows->icon_map->colormap=(Colormap) NULL;
5265 windows->pixel_info->pixels=(unsigned long *) NULL;
5266 windows->pixel_info->annotate_context=(GC) NULL;
5267 windows->pixel_info->highlight_context=(GC) NULL;
5268 windows->pixel_info->widget_context=(GC) NULL;
5269 windows->font_info=(XFontStruct *) NULL;
5270 windows->icon_pixel->annotate_context=(GC) NULL;
5271 windows->icon_pixel->pixels=(unsigned long *) NULL;
5275 *windows->icon_resources=(*resource_info);
5276 windows->icon_resources->visual_type=(char *) "default";
5277 windows->icon_resources->colormap=SharedColormap;
5278 windows->visual_info=
5279 XBestVisualInfo(display,windows->map_info,resource_info);
5280 windows->icon_visual=
5281 XBestVisualInfo(display,windows->icon_map,windows->icon_resources);
5282 if ((windows->visual_info == (XVisualInfo *) NULL) ||
5283 (windows->icon_visual == (XVisualInfo *) NULL))
5284 ThrowXWindowFatalException(XServerFatalError,"UnableToGetVisual",
5285 resource_info->visual_type);
5286 if (IsEventLogging())
5288 (void) LogMagickEvent(X11Event,GetMagickModule(),"Visual:");
5289 (void) LogMagickEvent(X11Event,GetMagickModule()," visual id: 0x%lx",
5290 windows->visual_info->visualid);
5291 (void) LogMagickEvent(X11Event,GetMagickModule()," class: %s",
5292 XVisualClassName(windows->visual_info->klass));
5293 (void) LogMagickEvent(X11Event,GetMagickModule()," depth: %d planes",
5294 windows->visual_info->depth);
5295 (void) LogMagickEvent(X11Event,GetMagickModule(),
5296 " size of colormap: %d entries",windows->visual_info->colormap_size);
5297 (void) LogMagickEvent(X11Event,GetMagickModule(),
5298 " red, green, blue masks: 0x%lx 0x%lx 0x%lx",
5299 windows->visual_info->red_mask,windows->visual_info->green_mask,
5300 windows->visual_info->blue_mask);
5301 (void) LogMagickEvent(X11Event,GetMagickModule(),
5302 " significant bits in color: %d bits",
5303 windows->visual_info->bits_per_rgb);
5306 Allocate class and manager hints.
5308 windows->class_hints=XAllocClassHint();
5309 windows->manager_hints=XAllocWMHints();
5310 if ((windows->class_hints == (XClassHint *) NULL) ||
5311 (windows->manager_hints == (XWMHints *) NULL))
5312 ThrowXWindowFatalException(ResourceLimitFatalError,
5313 "MemoryAllocationFailed","...");
5315 Determine group leader if we have one.
5317 root_window=XRootWindow(display,windows->visual_info->screen);
5318 windows->group_leader.id=(Window) NULL;
5319 if (resource_info->window_group != (char *) NULL)
5321 if (isdigit((unsigned char) *resource_info->window_group) != 0)
5322 windows->group_leader.id=XWindowByID(display,root_window,(Window)
5323 strtol((char *) resource_info->window_group,(char **) NULL,0));
5324 if (windows->group_leader.id == (Window) NULL)
5325 windows->group_leader.id=
5326 XWindowByName(display,root_window,resource_info->window_group);
5332 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
5336 % X M a k e C u r s o r %
5340 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
5342 % XMakeCursor() creates a crosshairs X11 cursor.
5344 % The format of the XMakeCursor method is:
5346 % Cursor XMakeCursor(Display *display,Window window,Colormap colormap,
5347 % char *background_color,char *foreground_color)
5349 % A description of each parameter follows:
5351 % o display: Specifies a connection to an X server; returned from
5354 % o window: Specifies the ID of the window for which the cursor is
5357 % o colormap: Specifies the ID of the colormap from which the background
5358 % and foreground color will be retrieved.
5360 % o background_color: Specifies the color to use for the cursor background.
5362 % o foreground_color: Specifies the color to use for the cursor foreground.
5365 MagickPrivate Cursor XMakeCursor(Display *display,Window window,
5366 Colormap colormap,char *background_color,char *foreground_color)
5368 #define scope_height 17
5369 #define scope_x_hot 8
5370 #define scope_y_hot 8
5371 #define scope_width 17
5373 static const unsigned char
5376 0x80, 0x03, 0x00, 0x80, 0x02, 0x00, 0x80, 0x02, 0x00, 0x80, 0x02,
5377 0x00, 0x80, 0x02, 0x00, 0x80, 0x02, 0x00, 0x80, 0x02, 0x00, 0x7f,
5378 0xfc, 0x01, 0x01, 0x00, 0x01, 0x7f, 0xfc, 0x01, 0x80, 0x02, 0x00,
5379 0x80, 0x02, 0x00, 0x80, 0x02, 0x00, 0x80, 0x02, 0x00, 0x80, 0x02,
5380 0x00, 0x80, 0x02, 0x00, 0x80, 0x03, 0x00
5384 0xc0, 0x07, 0x00, 0xc0, 0x07, 0x00, 0xc0, 0x06, 0x00, 0xc0, 0x06,
5385 0x00, 0xc0, 0x06, 0x00, 0xc0, 0x06, 0x00, 0xff, 0xfe, 0x01, 0x7f,
5386 0xfc, 0x01, 0x03, 0x80, 0x01, 0x7f, 0xfc, 0x01, 0xff, 0xfe, 0x01,
5387 0xc0, 0x06, 0x00, 0xc0, 0x06, 0x00, 0xc0, 0x06, 0x00, 0xc0, 0x06,
5388 0x00, 0xc0, 0x07, 0x00, 0xc0, 0x07, 0x00
5402 assert(display != (Display *) NULL);
5403 assert(window != (Window) NULL);
5404 assert(colormap != (Colormap) NULL);
5405 assert(background_color != (char *) NULL);
5406 assert(foreground_color != (char *) NULL);
5407 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",background_color);
5408 source=XCreateBitmapFromData(display,window,(char *) scope_bits,scope_width,
5410 mask=XCreateBitmapFromData(display,window,(char *) scope_mask_bits,
5411 scope_width,scope_height);
5412 if ((source == (Pixmap) NULL) || (mask == (Pixmap) NULL))
5414 ThrowXWindowFatalException(XServerError,"UnableToCreatePixmap","...");
5415 return((Cursor) NULL);
5417 (void) XParseColor(display,colormap,background_color,&background);
5418 (void) XParseColor(display,colormap,foreground_color,&foreground);
5419 cursor=XCreatePixmapCursor(display,source,mask,&foreground,&background,
5420 scope_x_hot,scope_y_hot);
5421 (void) XFreePixmap(display,source);
5422 (void) XFreePixmap(display,mask);
5427 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
5431 % X M a k e I m a g e %
5435 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
5437 % XMakeImage() creates an X11 image. If the image size differs from the X11
5438 % image size, the image is first resized.
5440 % The format of the XMakeImage method is:
5442 % MagickBooleanType XMakeImage(Display *display,
5443 % const XResourceInfo *resource_info,XWindowInfo *window,Image *image,
5444 % unsigned int width,unsigned int height,ExceptionInfo *exception)
5446 % A description of each parameter follows:
5448 % o display: Specifies a connection to an X server; returned from
5451 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
5453 % o window: Specifies a pointer to a XWindowInfo structure.
5455 % o image: the image.
5457 % o width: Specifies the width in pixels of the rectangular area to
5460 % o height: Specifies the height in pixels of the rectangular area to
5463 % o exception: return any errors or warnings in this structure.
5466 MagickPrivate MagickBooleanType XMakeImage(Display *display,
5467 const XResourceInfo *resource_info,XWindowInfo *window,Image *image,
5468 unsigned int width,unsigned int height,ExceptionInfo *exception)
5470 #define CheckOverflowException(length,width,height) \
5471 (((height) != 0) && ((length)/((size_t) height) != ((size_t) width)))
5484 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
5485 assert(display != (Display *) NULL);
5486 assert(resource_info != (XResourceInfo *) NULL);
5487 assert(window != (XWindowInfo *) NULL);
5489 assert(height != 0);
5490 if ((window->width == 0) || (window->height == 0))
5491 return(MagickFalse);
5493 Apply user transforms to the image.
5495 (void) XCheckDefineCursor(display,window->id,window->busy_cursor);
5496 (void) XFlush(display);
5497 depth=(int) window->depth;
5498 if (window->destroy)
5499 window->image=DestroyImage(window->image);
5500 window->image=image;
5501 window->destroy=MagickFalse;
5502 if (window->image != (Image *) NULL)
5504 if (window->crop_geometry != (char *) NULL)
5515 window->image->page.x=0;
5516 window->image->page.y=0;
5517 (void) ParsePageGeometry(window->image,window->crop_geometry,
5518 &crop_info,exception);
5519 crop_image=CropImage(window->image,&crop_info,exception);
5520 if (crop_image != (Image *) NULL)
5522 if (window->image != image)
5523 window->image=DestroyImage(window->image);
5524 window->image=crop_image;
5525 window->destroy=MagickTrue;
5528 if ((width != (unsigned int) window->image->columns) ||
5529 (height != (unsigned int) window->image->rows))
5537 resize_image=NewImageList();
5538 if (window->pixel_info->colors != 0)
5539 resize_image=SampleImage(window->image,width,height,exception);
5541 resize_image=ThumbnailImage(window->image,width,height,exception);
5542 if (resize_image != (Image *) NULL)
5544 if (window->image != image)
5545 window->image=DestroyImage(window->image);
5546 window->image=resize_image;
5547 window->destroy=MagickTrue;
5550 width=(unsigned int) window->image->columns;
5551 assert((size_t) width == window->image->columns);
5552 height=(unsigned int) window->image->rows;
5553 assert((size_t) height == window->image->rows);
5558 ximage=(XImage *) NULL;
5559 format=(depth == 1) ? XYBitmap : ZPixmap;
5560 #if defined(MAGICKCORE_HAVE_SHARED_MEMORY)
5561 if (window->shared_memory != MagickFalse)
5566 segment_info=(XShmSegmentInfo *) window->segment_info;
5567 segment_info[1].shmid=(-1);
5568 segment_info[1].shmaddr=(char *) NULL;
5569 ximage=XShmCreateImage(display,window->visual,(unsigned int) depth,format,
5570 (char *) NULL,&segment_info[1],width,height);
5571 if (ximage == (XImage *) NULL)
5572 window->shared_memory=MagickFalse;
5573 length=(size_t) ximage->bytes_per_line*ximage->height;
5574 if (CheckOverflowException(length,ximage->bytes_per_line,ximage->height))
5575 window->shared_memory=MagickFalse;
5576 if (window->shared_memory != MagickFalse)
5577 segment_info[1].shmid=shmget(IPC_PRIVATE,length,IPC_CREAT | 0777);
5578 if (window->shared_memory != MagickFalse)
5579 segment_info[1].shmaddr=(char *) shmat(segment_info[1].shmid,0,0);
5580 if (segment_info[1].shmid < 0)
5581 window->shared_memory=MagickFalse;
5582 if (window->shared_memory != MagickFalse)
5583 (void) shmctl(segment_info[1].shmid,IPC_RMID,0);
5586 if (ximage != (XImage *) NULL)
5587 XDestroyImage(ximage);
5588 ximage=(XImage *) NULL;
5589 if (segment_info[1].shmaddr)
5591 (void) shmdt(segment_info[1].shmaddr);
5592 segment_info[1].shmaddr=(char *) NULL;
5594 if (segment_info[1].shmid >= 0)
5596 (void) shmctl(segment_info[1].shmid,IPC_RMID,0);
5597 segment_info[1].shmid=(-1);
5603 Allocate X image pixel data.
5605 #if defined(MAGICKCORE_HAVE_SHARED_MEMORY)
5606 if (window->shared_memory)
5614 (void) XSync(display,MagickFalse);
5615 xerror_alert=MagickFalse;
5616 segment_info=(XShmSegmentInfo *) window->segment_info;
5617 ximage->data=segment_info[1].shmaddr;
5618 segment_info[1].readOnly=MagickFalse;
5619 status=XShmAttach(display,&segment_info[1]);
5620 if (status != False)
5621 (void) XSync(display,MagickFalse);
5622 if ((status == False) || (xerror_alert != MagickFalse))
5624 window->shared_memory=MagickFalse;
5625 if (status != False)
5626 XShmDetach(display,&segment_info[1]);
5627 if (ximage != (XImage *) NULL)
5630 XDestroyImage(ximage);
5631 ximage=(XImage *) NULL;
5633 if (segment_info[1].shmid >= 0)
5635 if (segment_info[1].shmaddr != NULL)
5636 (void) shmdt(segment_info[1].shmaddr);
5637 (void) shmctl(segment_info[1].shmid,IPC_RMID,0);
5638 segment_info[1].shmid=(-1);
5639 segment_info[1].shmaddr=(char *) NULL;
5644 if (window->shared_memory == MagickFalse)
5645 ximage=XCreateImage(display,window->visual,(unsigned int) depth,format,0,
5646 (char *) NULL,width,height,XBitmapPad(display),0);
5647 if (ximage == (XImage *) NULL)
5650 Unable to create X image.
5652 (void) XCheckDefineCursor(display,window->id,window->cursor);
5653 return(MagickFalse);
5655 length=(size_t) ximage->bytes_per_line*ximage->height;
5656 if (IsEventLogging())
5658 (void) LogMagickEvent(X11Event,GetMagickModule(),"XImage:");
5659 (void) LogMagickEvent(X11Event,GetMagickModule()," width, height: %dx%d",
5660 ximage->width,ximage->height);
5661 (void) LogMagickEvent(X11Event,GetMagickModule()," format: %d",
5663 (void) LogMagickEvent(X11Event,GetMagickModule()," byte order: %d",
5664 ximage->byte_order);
5665 (void) LogMagickEvent(X11Event,GetMagickModule(),
5666 " bitmap unit, bit order, pad: %d %d %d",ximage->bitmap_unit,
5667 ximage->bitmap_bit_order,ximage->bitmap_pad);
5668 (void) LogMagickEvent(X11Event,GetMagickModule()," depth: %d",
5670 (void) LogMagickEvent(X11Event,GetMagickModule()," bytes per line: %d",
5671 ximage->bytes_per_line);
5672 (void) LogMagickEvent(X11Event,GetMagickModule()," bits per pixel: %d",
5673 ximage->bits_per_pixel);
5674 (void) LogMagickEvent(X11Event,GetMagickModule(),
5675 " red, green, blue masks: 0x%lx 0x%lx 0x%lx",ximage->red_mask,
5676 ximage->green_mask,ximage->blue_mask);
5678 if (window->shared_memory == MagickFalse)
5680 if (ximage->format != XYBitmap)
5681 ximage->data=(char *) AcquireQuantumMemory((size_t)
5682 ximage->bytes_per_line,(size_t) ximage->height);
5684 ximage->data=(char *) AcquireQuantumMemory((size_t)
5685 ximage->bytes_per_line*ximage->depth,(size_t) ximage->height);
5687 if (ximage->data == (char *) NULL)
5690 Unable to allocate pixel data.
5692 XDestroyImage(ximage);
5693 ximage=(XImage *) NULL;
5694 (void) XCheckDefineCursor(display,window->id,window->cursor);
5695 return(MagickFalse);
5697 if (window->ximage != (XImage *) NULL)
5700 Destroy previous X image.
5702 length=(size_t) window->ximage->bytes_per_line*window->ximage->height;
5703 #if defined(MAGICKCORE_HAVE_SHARED_MEMORY)
5704 if (window->segment_info != (XShmSegmentInfo *) NULL)
5709 segment_info=(XShmSegmentInfo *) window->segment_info;
5710 if (segment_info[0].shmid >= 0)
5712 (void) XSync(display,MagickFalse);
5713 (void) XShmDetach(display,&segment_info[0]);
5714 (void) XSync(display,MagickFalse);
5715 if (segment_info[0].shmaddr != (char *) NULL)
5716 (void) shmdt(segment_info[0].shmaddr);
5717 (void) shmctl(segment_info[0].shmid,IPC_RMID,0);
5718 segment_info[0].shmid=(-1);
5719 segment_info[0].shmaddr=(char *) NULL;
5720 window->ximage->data=(char *) NULL;
5724 if (window->ximage->data != (char *) NULL)
5725 free(window->ximage->data);
5726 window->ximage->data=(char *) NULL;
5727 XDestroyImage(window->ximage);
5728 window->ximage=(XImage *) NULL;
5730 #if defined(MAGICKCORE_HAVE_SHARED_MEMORY)
5731 if (window->segment_info != (XShmSegmentInfo *) NULL)
5736 segment_info=(XShmSegmentInfo *) window->segment_info;
5737 segment_info[0]=segment_info[1];
5740 window->ximage=ximage;
5741 matte_image=(XImage *) NULL;
5742 if ((window->shape != MagickFalse) && (window->image != (Image *) NULL))
5743 if ((window->image->matte != MagickFalse) &&
5744 ((int) width <= XDisplayWidth(display,window->screen)) &&
5745 ((int) height <= XDisplayHeight(display,window->screen)))
5750 matte_image=XCreateImage(display,window->visual,1,XYBitmap,0,
5751 (char *) NULL,width,height,XBitmapPad(display),0);
5752 if (IsEventLogging())
5754 (void) LogMagickEvent(X11Event,GetMagickModule(),"Matte Image:");
5755 (void) LogMagickEvent(X11Event,GetMagickModule(),
5756 " width, height: %dx%d",matte_image->width,matte_image->height);
5758 if (matte_image != (XImage *) NULL)
5761 Allocate matte image pixel data.
5763 matte_image->data=(char *) AcquireQuantumMemory((size_t)
5764 matte_image->bytes_per_line*matte_image->depth,
5765 (size_t) matte_image->height);
5766 if (matte_image->data == (char *) NULL)
5768 XDestroyImage(matte_image);
5769 matte_image=(XImage *) NULL;
5773 if (window->matte_image != (XImage *) NULL)
5778 if (window->matte_image->data != (char *) NULL)
5779 free(window->matte_image->data);
5780 window->matte_image->data=(char *) NULL;
5781 XDestroyImage(window->matte_image);
5782 window->matte_image=(XImage *) NULL;
5784 window->matte_image=matte_image;
5785 if (window->matte_pixmap != (Pixmap) NULL)
5787 (void) XFreePixmap(display,window->matte_pixmap);
5788 window->matte_pixmap=(Pixmap) NULL;
5789 #if defined(MAGICKCORE_HAVE_SHAPE)
5790 if (window->shape != MagickFalse)
5791 XShapeCombineMask(display,window->id,ShapeBounding,0,0,None,ShapeSet);
5794 window->stasis=MagickFalse;
5796 Convert pixels to X image data.
5798 if (window->image != (Image *) NULL)
5800 if ((ximage->byte_order == LSBFirst) || ((ximage->format == XYBitmap) &&
5801 (ximage->bitmap_bit_order == LSBFirst)))
5802 XMakeImageLSBFirst(resource_info,window,window->image,ximage,
5803 matte_image,exception);
5805 XMakeImageMSBFirst(resource_info,window,window->image,ximage,
5806 matte_image,exception);
5808 if (window->matte_image != (XImage *) NULL)
5811 Create matte pixmap.
5813 window->matte_pixmap=XCreatePixmap(display,window->id,width,height,1);
5814 if (window->matte_pixmap != (Pixmap) NULL)
5823 Copy matte image to matte pixmap.
5825 context_values.background=0;
5826 context_values.foreground=1;
5827 graphics_context=XCreateGC(display,window->matte_pixmap,
5828 (size_t) (GCBackground | GCForeground),&context_values);
5829 (void) XPutImage(display,window->matte_pixmap,graphics_context,
5830 window->matte_image,0,0,0,0,width,height);
5831 (void) XFreeGC(display,graphics_context);
5832 #if defined(MAGICKCORE_HAVE_SHAPE)
5833 if (window->shape != MagickFalse)
5834 XShapeCombineMask(display,window->id,ShapeBounding,0,0,
5835 window->matte_pixmap,ShapeSet);
5839 (void) XMakePixmap(display,resource_info,window);
5843 (void) XCheckDefineCursor(display,window->id,window->cursor);
5848 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
5852 + X M a k e I m a g e L S B F i r s t %
5856 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
5858 % XMakeImageLSBFirst() initializes the pixel data of an X11 Image. The X image
5859 % pixels are copied in least-significant bit and byte first order. The
5860 % server's scanline pad is respected. Rather than using one or two general
5861 % cases, many special cases are found here to help speed up the image
5864 % The format of the XMakeImageLSBFirst method is:
5866 % void XMakeImageLSBFirst(Display *display,XWindows *windows,
5867 % ExceptionInfo *exception)
5869 % A description of each parameter follows:
5871 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
5873 % o window: Specifies a pointer to a XWindowInfo structure.
5875 % o image: the image.
5877 % o ximage: Specifies a pointer to a XImage structure; returned from
5880 % o matte_image: Specifies a pointer to a XImage structure; returned from
5883 % o exception: return any errors or warnings in this structure.
5886 static void XMakeImageLSBFirst(const XResourceInfo *resource_info,
5887 const XWindowInfo *window,Image *image,XImage *ximage,XImage *matte_image,
5888 ExceptionInfo *exception)
5899 register const Quantum
5905 register unsigned char
5922 assert(resource_info != (XResourceInfo *) NULL);
5923 assert(window != (XWindowInfo *) NULL);
5924 assert(image != (Image *) NULL);
5925 if (image->debug != MagickFalse)
5926 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
5928 if ((window->immutable == MagickFalse) &&
5929 (image->storage_class == DirectClass) && (image->matte != MagickFalse))
5932 size[MaxTextExtent];
5940 image_info=AcquireImageInfo();
5941 (void) CopyMagickString(image_info->filename,
5942 resource_info->image_info->texture != (char *) NULL ?
5943 resource_info->image_info->texture : "pattern:checkerboard",
5945 (void) FormatLocaleString(size,MaxTextExtent,"%.20gx%.20g",(double)
5946 image->columns,(double) image->rows);
5947 image_info->size=ConstantString(size);
5948 pattern=ReadImage(image_info,exception);
5949 image_info=DestroyImageInfo(image_info);
5950 if (pattern != (Image *) NULL)
5952 canvas=CloneImage(image,0,0,MagickTrue,exception);
5953 if (canvas != (Image *) NULL)
5954 (void) CompositeImage(canvas,DstOverCompositeOp,pattern,0,0,
5956 pattern=DestroyImage(pattern);
5959 scanline_pad=(unsigned int) (ximage->bytes_per_line-((ximage->width*
5960 ximage->bits_per_pixel) >> 3));
5961 map_info=window->map_info;
5962 pixels=window->pixel_info->pixels;
5963 q=(unsigned char *) ximage->data;
5965 canvas_view=AcquireCacheView(canvas);
5966 if (ximage->format == XYBitmap)
5968 register unsigned short
5976 Convert canvas to big-endian bitmap.
5978 background=(unsigned char)
5979 (XPixelIntensity(&window->pixel_info->foreground_color) <
5980 XPixelIntensity(&window->pixel_info->background_color) ? 0x80 : 0x00);
5981 foreground=(unsigned char)
5982 (XPixelIntensity(&window->pixel_info->background_color) <
5983 XPixelIntensity(&window->pixel_info->foreground_color) ? 0x80 : 0x00);
5984 polarity=(unsigned short) ((GetPixelInfoIntensity(
5985 &canvas->colormap[0])) < ((Quantum) QuantumRange/2) ? 1 : 0);
5986 if (canvas->colors == 2)
5987 polarity=GetPixelInfoIntensity(&canvas->colormap[0]) <
5988 GetPixelInfoIntensity(&canvas->colormap[1]);
5989 for (y=0; y < (int) canvas->rows; y++)
5991 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,canvas->columns,1,
5993 if (p == (const Quantum *) NULL)
5997 for (x=0; x < (int) canvas->columns; x++)
6000 if (GetPixelIndex(canvas,p) == (Quantum) polarity)
6011 p+=GetPixelChannels(canvas);
6019 if (window->pixel_info->colors != 0)
6020 switch (ximage->bits_per_pixel)
6024 register unsigned int
6028 Convert to 2 bit color-mapped X canvas.
6030 for (y=0; y < (int) canvas->rows; y++)
6032 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6033 canvas->columns,1,exception);
6034 if (p == (const Quantum *) NULL)
6037 for (x=0; x < (int) canvas->columns; x++)
6039 pixel=pixels[(ssize_t) GetPixelIndex(canvas,p)] & 0x0f;
6044 *q=(unsigned char) pixel;
6050 *q|=(unsigned char) (pixel << 2);
6056 *q|=(unsigned char) (pixel << 4);
6062 *q|=(unsigned char) (pixel << 6);
6068 p+=GetPixelChannels(canvas);
6076 register unsigned int
6080 Convert to 4 bit color-mapped X canvas.
6082 for (y=0; y < (int) canvas->rows; y++)
6084 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6085 canvas->columns,1,exception);
6086 if (p == (const Quantum *) NULL)
6089 for (x=0; x < (int) canvas->columns; x++)
6091 pixel=pixels[(ssize_t) GetPixelIndex(canvas,p)] & 0xf;
6096 *q=(unsigned char) pixel;
6102 *q|=(unsigned char) (pixel << 4);
6108 p+=GetPixelChannels(canvas);
6118 Convert to 8 bit color-mapped X canvas.
6120 if (resource_info->color_recovery &&
6121 resource_info->quantize_info->dither)
6123 XDitherImage(canvas,ximage,exception);
6126 for (y=0; y < (int) canvas->rows; y++)
6128 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6129 canvas->columns,1,exception);
6130 if (p == (const Quantum *) NULL)
6132 for (x=0; x < (int) canvas->columns; x++)
6134 pixel=pixels[(ssize_t) GetPixelIndex(canvas,p)];
6135 *q++=(unsigned char) pixel;
6136 p+=GetPixelChannels(canvas);
6147 register unsigned int
6151 channel[sizeof(size_t)];
6154 Convert to multi-byte color-mapped X canvas.
6156 bytes_per_pixel=(unsigned int) (ximage->bits_per_pixel >> 3);
6157 for (y=0; y < (int) canvas->rows; y++)
6159 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6160 canvas->columns,1,exception);
6161 if (p == (const Quantum *) NULL)
6163 for (x=0; x < (int) canvas->columns; x++)
6165 pixel=pixels[(ssize_t) GetPixelIndex(canvas,p)];
6166 for (k=0; k < (int) bytes_per_pixel; k++)
6168 channel[k]=(unsigned char) pixel;
6171 for (k=0; k < (int) bytes_per_pixel; k++)
6173 p+=GetPixelChannels(canvas);
6181 switch (ximage->bits_per_pixel)
6185 register unsigned int
6189 Convert to contiguous 2 bit continuous-tone X canvas.
6191 for (y=0; y < (int) canvas->rows; y++)
6194 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6195 canvas->columns,1,exception);
6196 if (p == (const Quantum *) NULL)
6198 for (x=0; x < (int) canvas->columns; x++)
6200 pixel=XGammaPixel(canvas,map_info,p);
6206 *q=(unsigned char) pixel;
6212 *q|=(unsigned char) (pixel << 2);
6218 *q|=(unsigned char) (pixel << 4);
6224 *q|=(unsigned char) (pixel << 6);
6230 p+=GetPixelChannels(canvas);
6238 register unsigned int
6242 Convert to contiguous 4 bit continuous-tone X canvas.
6244 for (y=0; y < (int) canvas->rows; y++)
6246 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6247 canvas->columns,1,exception);
6248 if (p == (const Quantum *) NULL)
6251 for (x=0; x < (int) canvas->columns; x++)
6253 pixel=XGammaPixel(canvas,map_info,p);
6259 *q=(unsigned char) pixel;
6265 *q|=(unsigned char) (pixel << 4);
6271 p+=GetPixelChannels(canvas);
6281 Convert to contiguous 8 bit continuous-tone X canvas.
6283 if (resource_info->color_recovery &&
6284 resource_info->quantize_info->dither)
6286 XDitherImage(canvas,ximage,exception);
6289 for (y=0; y < (int) canvas->rows; y++)
6291 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6292 canvas->columns,1,exception);
6293 if (p == (const Quantum *) NULL)
6295 for (x=0; x < (int) canvas->columns; x++)
6297 pixel=XGammaPixel(canvas,map_info,p);
6298 *q++=(unsigned char) pixel;
6299 p+=GetPixelChannels(canvas);
6307 if ((ximage->bits_per_pixel == 32) && (map_info->red_max == 255) &&
6308 (map_info->green_max == 255) && (map_info->blue_max == 255) &&
6309 (map_info->red_mult == 65536L) && (map_info->green_mult == 256) &&
6310 (map_info->blue_mult == 1))
6313 Convert to 32 bit continuous-tone X canvas.
6315 for (y=0; y < (int) canvas->rows; y++)
6317 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6318 canvas->columns,1,exception);
6319 if (p == (const Quantum *) NULL)
6321 if ((red_gamma != 1.0) || (green_gamma != 1.0) ||
6322 (blue_gamma != 1.0))
6325 Gamma correct canvas.
6327 for (x=(int) canvas->columns-1; x >= 0; x--)
6329 *q++=ScaleQuantumToChar(XBlueGamma(
6330 GetPixelBlue(canvas,p)));
6331 *q++=ScaleQuantumToChar(XGreenGamma(
6332 GetPixelGreen(canvas,p)));
6333 *q++=ScaleQuantumToChar(XRedGamma(
6334 GetPixelRed(canvas,p)));
6336 p+=GetPixelChannels(canvas);
6340 for (x=(int) canvas->columns-1; x >= 0; x--)
6342 *q++=ScaleQuantumToChar((Quantum)
6343 GetPixelBlue(canvas,p));
6344 *q++=ScaleQuantumToChar((Quantum)
6345 GetPixelGreen(canvas,p));
6346 *q++=ScaleQuantumToChar((Quantum)
6347 GetPixelRed(canvas,p));
6349 p+=GetPixelChannels(canvas);
6354 if ((ximage->bits_per_pixel == 32) && (map_info->red_max == 255) &&
6355 (map_info->green_max == 255) && (map_info->blue_max == 255) &&
6356 (map_info->red_mult == 1) && (map_info->green_mult == 256) &&
6357 (map_info->blue_mult == 65536L))
6360 Convert to 32 bit continuous-tone X canvas.
6362 for (y=0; y < (int) canvas->rows; y++)
6364 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6365 canvas->columns,1,exception);
6366 if (p == (const Quantum *) NULL)
6368 if ((red_gamma != 1.0) || (green_gamma != 1.0) ||
6369 (blue_gamma != 1.0))
6372 Gamma correct canvas.
6374 for (x=(int) canvas->columns-1; x >= 0; x--)
6376 *q++=ScaleQuantumToChar(XRedGamma(
6377 GetPixelRed(canvas,p)));
6378 *q++=ScaleQuantumToChar(XGreenGamma(
6379 GetPixelGreen(canvas,p)));
6380 *q++=ScaleQuantumToChar(XBlueGamma(
6381 GetPixelBlue(canvas,p)));
6383 p+=GetPixelChannels(canvas);
6387 for (x=(int) canvas->columns-1; x >= 0; x--)
6389 *q++=ScaleQuantumToChar((Quantum)
6390 GetPixelRed(canvas,p));
6391 *q++=ScaleQuantumToChar((Quantum)
6392 GetPixelGreen(canvas,p));
6393 *q++=ScaleQuantumToChar((Quantum)
6394 GetPixelBlue(canvas,p));
6396 p+=GetPixelChannels(canvas);
6405 register unsigned int
6409 channel[sizeof(size_t)];
6412 Convert to multi-byte continuous-tone X canvas.
6414 bytes_per_pixel=(unsigned int) (ximage->bits_per_pixel >> 3);
6415 for (y=0; y < (int) canvas->rows; y++)
6417 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6418 canvas->columns,1,exception);
6419 if (p == (const Quantum *) NULL)
6421 for (x=0; x < (int) canvas->columns; x++)
6423 pixel=XGammaPixel(canvas,map_info,p);
6424 for (k=0; k < (int) bytes_per_pixel; k++)
6426 channel[k]=(unsigned char) pixel;
6429 for (k=0; k < (int) bytes_per_pixel; k++)
6431 p+=GetPixelChannels(canvas);
6439 if (matte_image != (XImage *) NULL)
6442 Initialize matte canvas.
6444 scanline_pad=(unsigned int) (matte_image->bytes_per_line-
6445 ((matte_image->width*matte_image->bits_per_pixel) >> 3));
6446 q=(unsigned char *) matte_image->data;
6447 for (y=0; y < (int) canvas->rows; y++)
6449 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,canvas->columns,1,
6451 if (p == (const Quantum *) NULL)
6455 for (x=(int) canvas->columns-1; x >= 0; x--)
6458 if (GetPixelAlpha(canvas,p) > (QuantumRange/2))
6467 p+=GetPixelChannels(canvas);
6474 canvas_view=DestroyCacheView(canvas_view);
6475 if (canvas != image)
6476 canvas=DestroyImage(canvas);
6480 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
6484 + X M a k e I m a g e M S B F i r s t %
6488 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
6490 % XMakeImageMSBFirst() initializes the pixel data of an X11 Image. The X
6491 % image pixels are copied in most-significant bit and byte first order. The
6492 % server's scanline pad is also respected. Rather than using one or two
6493 % general cases, many special cases are found here to help speed up the image
6496 % The format of the XMakeImageMSBFirst method is:
6498 % XMakeImageMSBFirst(resource_info,window,image,ximage,matte_image,
6499 % ExceptionInfo *exception)
6501 % A description of each parameter follows:
6503 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
6505 % o window: Specifies a pointer to a XWindowInfo structure.
6507 % o image: the image.
6509 % o ximage: Specifies a pointer to a XImage structure; returned from
6512 % o matte_image: Specifies a pointer to a XImage structure; returned from
6515 % o exception: return any errors or warnings in this structure.
6518 static void XMakeImageMSBFirst(const XResourceInfo *resource_info,
6519 const XWindowInfo *window,Image *image,XImage *ximage,XImage *matte_image,
6520 ExceptionInfo *exception)
6534 register const Quantum
6537 register unsigned char
6554 assert(resource_info != (XResourceInfo *) NULL);
6555 assert(window != (XWindowInfo *) NULL);
6556 assert(image != (Image *) NULL);
6557 if (image->debug != MagickFalse)
6558 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
6560 if ((window->immutable != MagickFalse) &&
6561 (image->storage_class == DirectClass) && (image->matte != MagickFalse))
6564 size[MaxTextExtent];
6572 image_info=AcquireImageInfo();
6573 (void) CopyMagickString(image_info->filename,
6574 resource_info->image_info->texture != (char *) NULL ?
6575 resource_info->image_info->texture : "pattern:checkerboard",
6577 (void) FormatLocaleString(size,MaxTextExtent,"%.20gx%.20g",(double)
6578 image->columns,(double) image->rows);
6579 image_info->size=ConstantString(size);
6580 pattern=ReadImage(image_info,exception);
6581 image_info=DestroyImageInfo(image_info);
6582 if (pattern != (Image *) NULL)
6584 canvas=CloneImage(image,0,0,MagickTrue,exception);
6585 if (canvas != (Image *) NULL)
6586 (void) CompositeImage(canvas,DstOverCompositeOp,pattern,0,0,
6588 pattern=DestroyImage(pattern);
6591 scanline_pad=(unsigned int) (ximage->bytes_per_line-((ximage->width*
6592 ximage->bits_per_pixel) >> 3));
6593 map_info=window->map_info;
6594 pixels=window->pixel_info->pixels;
6595 q=(unsigned char *) ximage->data;
6597 canvas_view=AcquireCacheView(canvas);
6598 if (ximage->format == XYBitmap)
6600 register unsigned short
6608 Convert canvas to big-endian bitmap.
6610 background=(unsigned char)
6611 (XPixelIntensity(&window->pixel_info->foreground_color) <
6612 XPixelIntensity(&window->pixel_info->background_color) ? 0x01 : 0x00);
6613 foreground=(unsigned char)
6614 (XPixelIntensity(&window->pixel_info->background_color) <
6615 XPixelIntensity(&window->pixel_info->foreground_color) ? 0x01 : 0x00);
6616 polarity=(unsigned short) ((GetPixelInfoIntensity(
6617 &canvas->colormap[0])) < ((Quantum) QuantumRange/2) ? 1 : 0);
6618 if (canvas->colors == 2)
6619 polarity=GetPixelInfoIntensity(&canvas->colormap[0]) <
6620 GetPixelInfoIntensity(&canvas->colormap[1]);
6621 for (y=0; y < (int) canvas->rows; y++)
6623 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,canvas->columns,1,
6625 if (p == (const Quantum *) NULL)
6629 for (x=(int) canvas->columns-1; x >= 0; x--)
6632 if (GetPixelIndex(canvas,p) == (Quantum) polarity)
6643 p+=GetPixelChannels(canvas);
6651 if (window->pixel_info->colors != 0)
6652 switch (ximage->bits_per_pixel)
6656 register unsigned int
6660 Convert to 2 bit color-mapped X canvas.
6662 for (y=0; y < (int) canvas->rows; y++)
6664 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6665 canvas->columns,1,exception);
6666 if (p == (const Quantum *) NULL)
6669 for (x=0; x < (int) canvas->columns; x++)
6671 pixel=pixels[(ssize_t)
6672 GetPixelIndex(canvas,p)] & 0xf;
6677 *q=(unsigned char) (pixel << 6);
6683 *q|=(unsigned char) (pixel << 4);
6689 *q|=(unsigned char) (pixel << 2);
6695 *q|=(unsigned char) pixel;
6701 p+=GetPixelChannels(canvas);
6709 register unsigned int
6713 Convert to 4 bit color-mapped X canvas.
6715 for (y=0; y < (int) canvas->rows; y++)
6717 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6718 canvas->columns,1,exception);
6719 if (p == (const Quantum *) NULL)
6722 for (x=0; x < (int) canvas->columns; x++)
6724 pixel=pixels[(ssize_t)
6725 GetPixelIndex(canvas,p)] & 0xf;
6730 *q=(unsigned char) (pixel << 4);
6736 *q|=(unsigned char) pixel;
6742 p+=GetPixelChannels(canvas);
6752 Convert to 8 bit color-mapped X canvas.
6754 if (resource_info->color_recovery &&
6755 resource_info->quantize_info->dither)
6757 XDitherImage(canvas,ximage,exception);
6760 for (y=0; y < (int) canvas->rows; y++)
6762 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6763 canvas->columns,1,exception);
6764 if (p == (const Quantum *) NULL)
6766 for (x=0; x < (int) canvas->columns; x++)
6768 pixel=pixels[(ssize_t) GetPixelIndex(canvas,p)];
6769 *q++=(unsigned char) pixel;
6770 p+=GetPixelChannels(canvas);
6781 register unsigned int
6785 channel[sizeof(size_t)];
6788 Convert to 8 bit color-mapped X canvas.
6790 bytes_per_pixel=(unsigned int) (ximage->bits_per_pixel >> 3);
6791 for (y=0; y < (int) canvas->rows; y++)
6793 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6794 canvas->columns,1,exception);
6795 if (p == (const Quantum *) NULL)
6797 for (x=0; x < (int) canvas->columns; x++)
6799 pixel=pixels[(ssize_t)
6800 GetPixelIndex(canvas,p)];
6801 for (k=(int) bytes_per_pixel-1; k >= 0; k--)
6803 channel[k]=(unsigned char) pixel;
6806 for (k=0; k < (int) bytes_per_pixel; k++)
6808 p+=GetPixelChannels(canvas);
6816 switch (ximage->bits_per_pixel)
6820 register unsigned int
6824 Convert to 4 bit continuous-tone X canvas.
6826 for (y=0; y < (int) canvas->rows; y++)
6828 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6829 canvas->columns,1,exception);
6830 if (p == (const Quantum *) NULL)
6833 for (x=(int) canvas->columns-1; x >= 0; x--)
6835 pixel=XGammaPixel(canvas,map_info,p);
6841 *q=(unsigned char) (pixel << 6);
6847 *q|=(unsigned char) (pixel << 4);
6853 *q|=(unsigned char) (pixel << 2);
6859 *q|=(unsigned char) pixel;
6865 p+=GetPixelChannels(canvas);
6873 register unsigned int
6877 Convert to 4 bit continuous-tone X canvas.
6879 for (y=0; y < (int) canvas->rows; y++)
6881 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6882 canvas->columns,1,exception);
6883 if (p == (const Quantum *) NULL)
6886 for (x=(int) canvas->columns-1; x >= 0; x--)
6888 pixel=XGammaPixel(canvas,map_info,p);
6894 *q=(unsigned char) (pixel << 4);
6900 *q|=(unsigned char) pixel;
6906 p+=GetPixelChannels(canvas);
6916 Convert to 8 bit continuous-tone X canvas.
6918 if (resource_info->color_recovery &&
6919 resource_info->quantize_info->dither)
6921 XDitherImage(canvas,ximage,exception);
6924 for (y=0; y < (int) canvas->rows; y++)
6926 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6927 canvas->columns,1,exception);
6928 if (p == (const Quantum *) NULL)
6930 for (x=(int) canvas->columns-1; x >= 0; x--)
6932 pixel=XGammaPixel(canvas,map_info,p);
6933 *q++=(unsigned char) pixel;
6934 p+=GetPixelChannels(canvas);
6942 if ((ximage->bits_per_pixel == 32) && (map_info->red_max == 255) &&
6943 (map_info->green_max == 255) && (map_info->blue_max == 255) &&
6944 (map_info->red_mult == 65536L) && (map_info->green_mult == 256) &&
6945 (map_info->blue_mult == 1))
6948 Convert to 32 bit continuous-tone X canvas.
6950 for (y=0; y < (int) canvas->rows; y++)
6952 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
6953 canvas->columns,1,exception);
6954 if (p == (const Quantum *) NULL)
6956 if ((red_gamma != 1.0) || (green_gamma != 1.0) ||
6957 (blue_gamma != 1.0))
6960 Gamma correct canvas.
6962 for (x=(int) canvas->columns-1; x >= 0; x--)
6965 *q++=ScaleQuantumToChar(XRedGamma(
6966 GetPixelRed(canvas,p)));
6967 *q++=ScaleQuantumToChar(XGreenGamma(
6968 GetPixelGreen(canvas,p)));
6969 *q++=ScaleQuantumToChar(XBlueGamma(
6970 GetPixelBlue(canvas,p)));
6971 p+=GetPixelChannels(canvas);
6975 for (x=(int) canvas->columns-1; x >= 0; x--)
6978 *q++=ScaleQuantumToChar((Quantum)
6979 GetPixelRed(canvas,p));
6980 *q++=ScaleQuantumToChar((Quantum)
6981 GetPixelGreen(canvas,p));
6982 *q++=ScaleQuantumToChar((Quantum)
6983 GetPixelBlue(canvas,p));
6984 p+=GetPixelChannels(canvas);
6989 if ((ximage->bits_per_pixel == 32) && (map_info->red_max == 255) &&
6990 (map_info->green_max == 255) && (map_info->blue_max == 255) &&
6991 (map_info->red_mult == 1) && (map_info->green_mult == 256) &&
6992 (map_info->blue_mult == 65536L))
6995 Convert to 32 bit continuous-tone X canvas.
6997 for (y=0; y < (int) canvas->rows; y++)
6999 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
7000 canvas->columns,1,exception);
7001 if (p == (const Quantum *) NULL)
7003 if ((red_gamma != 1.0) || (green_gamma != 1.0) ||
7004 (blue_gamma != 1.0))
7007 Gamma correct canvas.
7009 for (x=(int) canvas->columns-1; x >= 0; x--)
7012 *q++=ScaleQuantumToChar(XBlueGamma(
7013 GetPixelBlue(canvas,p)));
7014 *q++=ScaleQuantumToChar(XGreenGamma(
7015 GetPixelGreen(canvas,p)));
7016 *q++=ScaleQuantumToChar(XRedGamma(
7017 GetPixelRed(canvas,p)));
7018 p+=GetPixelChannels(canvas);
7022 for (x=(int) canvas->columns-1; x >= 0; x--)
7025 *q++=ScaleQuantumToChar((Quantum)
7026 GetPixelBlue(canvas,p));
7027 *q++=ScaleQuantumToChar((Quantum)
7028 GetPixelGreen(canvas,p));
7029 *q++=ScaleQuantumToChar((Quantum)
7030 GetPixelRed(canvas,p));
7031 p+=GetPixelChannels(canvas);
7040 register unsigned int
7044 channel[sizeof(size_t)];
7047 Convert to multi-byte continuous-tone X canvas.
7049 bytes_per_pixel=(unsigned int) (ximage->bits_per_pixel >> 3);
7050 for (y=0; y < (int) canvas->rows; y++)
7052 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,
7053 canvas->columns,1,exception);
7054 if (p == (const Quantum *) NULL)
7056 for (x=(int) canvas->columns-1; x >= 0; x--)
7058 pixel=XGammaPixel(canvas,map_info,p);
7059 for (k=(int) bytes_per_pixel-1; k >= 0; k--)
7061 channel[k]=(unsigned char) pixel;
7064 for (k=0; k < (int) bytes_per_pixel; k++)
7066 p+=GetPixelChannels(canvas);
7074 if (matte_image != (XImage *) NULL)
7077 Initialize matte canvas.
7079 scanline_pad=(unsigned int) (matte_image->bytes_per_line-
7080 ((matte_image->width*matte_image->bits_per_pixel) >> 3));
7081 q=(unsigned char *) matte_image->data;
7082 for (y=0; y < (int) canvas->rows; y++)
7084 p=GetCacheViewVirtualPixels(canvas_view,0,(ssize_t) y,canvas->columns,1,
7086 if (p == (const Quantum *) NULL)
7090 for (x=(int) canvas->columns-1; x >= 0; x--)
7093 if (GetPixelAlpha(canvas,p) > (QuantumRange/2))
7102 p+=GetPixelChannels(canvas);
7109 canvas_view=DestroyCacheView(canvas_view);
7110 if (canvas != image)
7111 canvas=DestroyImage(canvas);
7115 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
7119 % X M a k e M a g n i f y I m a g e %
7123 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
7125 % XMakeMagnifyImage() magnifies a region of an X image and displays it.
7127 % The format of the XMakeMagnifyImage method is:
7129 % void XMakeMagnifyImage(Display *display,XWindows *windows,
7130 % ExceptionInfo *exception)
7132 % A description of each parameter follows:
7134 % o display: Specifies a connection to an X server; returned from
7137 % o windows: Specifies a pointer to a XWindows structure.
7139 % o exception: return any errors or warnings in this structure.
7142 MagickPrivate void XMakeMagnifyImage(Display *display,XWindows *windows,
7143 ExceptionInfo *exception)
7146 tuple[MaxTextExtent];
7160 register unsigned char
7168 previous_magnify = 0;
7186 Check boundary conditions.
7188 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
7189 assert(display != (Display *) NULL);
7190 assert(windows != (XWindows *) NULL);
7192 for (n=1; n < (ssize_t) windows->magnify.data; n++)
7194 while ((magnify*windows->image.ximage->width) < windows->magnify.width)
7196 while ((magnify*windows->image.ximage->height) < windows->magnify.height)
7198 while (magnify > windows->magnify.width)
7200 while (magnify > windows->magnify.height)
7202 if (magnify != previous_magnify)
7211 New magnify factor: update magnify window name.
7214 while ((1 << i) <= (int) magnify)
7216 (void) FormatLocaleString(windows->magnify.name,MaxTextExtent,
7217 "Magnify %.20gX",(double) i);
7218 status=XStringListToTextProperty(&windows->magnify.name,1,&window_name);
7219 if (status != False)
7221 XSetWMName(display,windows->magnify.id,&window_name);
7222 XSetWMIconName(display,windows->magnify.id,&window_name);
7223 (void) XFree((void *) window_name.value);
7226 previous_magnify=magnify;
7227 ximage=windows->image.ximage;
7228 width=(unsigned int) windows->magnify.ximage->width;
7229 height=(unsigned int) windows->magnify.ximage->height;
7230 if ((windows->magnify.x < 0) ||
7231 (windows->magnify.x >= windows->image.ximage->width))
7232 windows->magnify.x=windows->image.ximage->width >> 1;
7233 x=windows->magnify.x-((width/magnify) >> 1);
7237 if (x > (int) (ximage->width-(width/magnify)))
7238 x=ximage->width-width/magnify;
7239 if ((windows->magnify.y < 0) ||
7240 (windows->magnify.y >= windows->image.ximage->height))
7241 windows->magnify.y=windows->image.ximage->height >> 1;
7242 y=windows->magnify.y-((height/magnify) >> 1);
7246 if (y > (int) (ximage->height-(height/magnify)))
7247 y=ximage->height-height/magnify;
7248 q=(unsigned char *) windows->magnify.ximage->data;
7249 scanline_pad=(unsigned int) (windows->magnify.ximage->bytes_per_line-
7250 ((width*windows->magnify.ximage->bits_per_pixel) >> 3));
7251 if (ximage->bits_per_pixel < 8)
7253 register unsigned char
7260 register unsigned int
7266 pixel_info=windows->magnify.pixel_info;
7267 switch (ximage->bitmap_bit_order)
7272 Magnify little-endian bitmap.
7276 if (ximage->format == XYBitmap)
7278 background=(unsigned char)
7279 (XPixelIntensity(&pixel_info->foreground_color) <
7280 XPixelIntensity(&pixel_info->background_color) ? 0x80 : 0x00);
7281 foreground=(unsigned char)
7282 (XPixelIntensity(&pixel_info->background_color) <
7283 XPixelIntensity(&pixel_info->foreground_color) ? 0x80 : 0x00);
7284 if (windows->magnify.depth > 1)
7285 Swap(background,foreground);
7287 for (i=0; i < (ssize_t) height; i+=magnify)
7290 Propogate pixel magnify rows.
7292 for (j=0; j < magnify; j++)
7294 p=(unsigned char *) ximage->data+y*ximage->bytes_per_line+
7295 ((x*ximage->bits_per_pixel) >> 3);
7296 p_bit=(unsigned char) (x*ximage->bits_per_pixel) & 0x07;
7299 for (k=0; k < width; k+=magnify)
7302 Propogate pixel magnify columns.
7304 for (l=0; l < magnify; l++)
7307 Propogate each bit plane.
7309 for (plane=0; (int) plane < ximage->bits_per_pixel; plane++)
7312 if (*p & (0x01 << (p_bit+plane)))
7325 p_bit+=ximage->bits_per_pixel;
7332 *q=byte >> (8-q_bit);
7344 Magnify big-endian bitmap.
7348 if (ximage->format == XYBitmap)
7350 background=(unsigned char)
7351 (XPixelIntensity(&pixel_info->foreground_color) <
7352 XPixelIntensity(&pixel_info->background_color) ? 0x01 : 0x00);
7353 foreground=(unsigned char)
7354 (XPixelIntensity(&pixel_info->background_color) <
7355 XPixelIntensity(&pixel_info->foreground_color) ? 0x01 : 0x00);
7356 if (windows->magnify.depth > 1)
7357 Swap(background,foreground);
7359 for (i=0; i < (ssize_t) height; i+=magnify)
7362 Propogate pixel magnify rows.
7364 for (j=0; j < magnify; j++)
7366 p=(unsigned char *) ximage->data+y*ximage->bytes_per_line+
7367 ((x*ximage->bits_per_pixel) >> 3);
7368 p_bit=(unsigned char) (x*ximage->bits_per_pixel) & 0x07;
7371 for (k=0; k < width; k+=magnify)
7374 Propogate pixel magnify columns.
7376 for (l=0; l < magnify; l++)
7379 Propogate each bit plane.
7381 for (plane=0; (int) plane < ximage->bits_per_pixel; plane++)
7384 if (*p & (0x80 >> (p_bit+plane)))
7397 p_bit+=ximage->bits_per_pixel;
7404 *q=byte << (8-q_bit);
7415 switch (ximage->bits_per_pixel)
7421 Magnify 8 bit X image.
7423 for (i=0; i < (ssize_t) height; i+=magnify)
7426 Propogate pixel magnify rows.
7428 for (j=0; j < magnify; j++)
7430 p=(unsigned char *) ximage->data+y*ximage->bytes_per_line+
7431 ((x*ximage->bits_per_pixel) >> 3);
7432 for (k=0; k < width; k+=magnify)
7435 Propogate pixel magnify columns.
7437 for (l=0; l < magnify; l++)
7449 register unsigned int
7454 Magnify multi-byte X image.
7456 bytes_per_pixel=(unsigned int) ximage->bits_per_pixel >> 3;
7457 for (i=0; i < (ssize_t) height; i+=magnify)
7460 Propogate pixel magnify rows.
7462 for (j=0; j < magnify; j++)
7464 p=(unsigned char *) ximage->data+y*ximage->bytes_per_line+
7465 ((x*ximage->bits_per_pixel) >> 3);
7466 for (k=0; k < width; k+=magnify)
7469 Propogate pixel magnify columns.
7471 for (l=0; l < magnify; l++)
7472 for (m=0; m < bytes_per_pixel; m++)
7484 Copy X image to magnify pixmap.
7486 x=windows->magnify.x-((width/magnify) >> 1);
7488 x=(int) ((width >> 1)-windows->magnify.x*magnify);
7490 if (x > (int) (ximage->width-(width/magnify)))
7491 x=(int) ((ximage->width-windows->magnify.x)*magnify-(width >> 1));
7494 y=windows->magnify.y-((height/magnify) >> 1);
7496 y=(int) ((height >> 1)-windows->magnify.y*magnify);
7498 if (y > (int) (ximage->height-(height/magnify)))
7499 y=(int) ((ximage->height-windows->magnify.y)*magnify-(height >> 1));
7502 if ((x != 0) || (y != 0))
7503 (void) XFillRectangle(display,windows->magnify.pixmap,
7504 windows->magnify.annotate_context,0,0,width,height);
7505 (void) XPutImage(display,windows->magnify.pixmap,
7506 windows->magnify.annotate_context,windows->magnify.ximage,0,0,x,y,width-x,
7508 if ((magnify > 1) && ((magnify <= (width >> 1)) &&
7509 (magnify <= (height >> 1))))
7515 Highlight center pixel.
7517 highlight_info.x=(ssize_t) windows->magnify.width >> 1;
7518 highlight_info.y=(ssize_t) windows->magnify.height >> 1;
7519 highlight_info.width=magnify;
7520 highlight_info.height=magnify;
7521 (void) XDrawRectangle(display,windows->magnify.pixmap,
7522 windows->magnify.highlight_context,(int) highlight_info.x,
7523 (int) highlight_info.y,(unsigned int) highlight_info.width-1,
7524 (unsigned int) highlight_info.height-1);
7526 (void) XDrawRectangle(display,windows->magnify.pixmap,
7527 windows->magnify.annotate_context,(int) highlight_info.x+1,
7528 (int) highlight_info.y+1,(unsigned int) highlight_info.width-3,
7529 (unsigned int) highlight_info.height-3);
7532 Show center pixel color.
7534 (void) GetOneVirtualPixelInfo(windows->image.image,TileVirtualPixelMethod,
7535 (ssize_t) windows->magnify.x,(ssize_t) windows->magnify.y,&pixel,exception);
7536 (void) FormatLocaleString(tuple,MaxTextExtent,"%d,%d: ",
7537 windows->magnify.x,windows->magnify.y);
7538 (void) ConcatenateMagickString(tuple,"(",MaxTextExtent);
7539 ConcatenateColorComponent(&pixel,RedPixelChannel,X11Compliance,tuple);
7540 (void) ConcatenateMagickString(tuple,",",MaxTextExtent);
7541 ConcatenateColorComponent(&pixel,GreenPixelChannel,X11Compliance,tuple);
7542 (void) ConcatenateMagickString(tuple,",",MaxTextExtent);
7543 ConcatenateColorComponent(&pixel,BluePixelChannel,X11Compliance,tuple);
7544 if (pixel.colorspace == CMYKColorspace)
7546 (void) ConcatenateMagickString(tuple,",",MaxTextExtent);
7547 ConcatenateColorComponent(&pixel,BlackPixelChannel,X11Compliance,tuple);
7549 if (pixel.matte != MagickFalse)
7551 (void) ConcatenateMagickString(tuple,",",MaxTextExtent);
7552 ConcatenateColorComponent(&pixel,AlphaPixelChannel,X11Compliance,tuple);
7554 (void) ConcatenateMagickString(tuple,")",MaxTextExtent);
7555 height=(unsigned int) windows->magnify.font_info->ascent+
7556 windows->magnify.font_info->descent;
7557 x=windows->magnify.font_info->max_bounds.width >> 1;
7558 y=windows->magnify.font_info->ascent+(height >> 2);
7559 (void) XDrawImageString(display,windows->magnify.pixmap,
7560 windows->magnify.annotate_context,x,y,tuple,(int) strlen(tuple));
7561 GetColorTuple(&pixel,MagickTrue,tuple);
7563 (void) XDrawImageString(display,windows->magnify.pixmap,
7564 windows->magnify.annotate_context,x,y,tuple,(int) strlen(tuple));
7565 (void) QueryColorname(windows->image.image,&pixel,SVGCompliance,tuple,
7568 (void) XDrawImageString(display,windows->magnify.pixmap,
7569 windows->magnify.annotate_context,x,y,tuple,(int) strlen(tuple));
7571 Refresh magnify window.
7573 magnify_window=windows->magnify;
7576 XRefreshWindow(display,&magnify_window,(XEvent *) NULL);
7580 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
7584 % X M a k e P i x m a p %
7588 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
7590 % XMakePixmap() creates an X11 pixmap.
7592 % The format of the XMakePixmap method is:
7594 % void XMakeStandardColormap(Display *display,XVisualInfo *visual_info,
7595 % XResourceInfo *resource_info,Image *image,XStandardColormap *map_info,
7596 % XPixelInfo *pixel)
7598 % A description of each parameter follows:
7600 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
7602 % o display: Specifies a connection to an X server; returned from
7605 % o window: Specifies a pointer to a XWindowInfo structure.
7608 static MagickBooleanType XMakePixmap(Display *display,
7609 const XResourceInfo *resource_info,XWindowInfo *window)
7615 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
7616 assert(display != (Display *) NULL);
7617 assert(resource_info != (XResourceInfo *) NULL);
7618 assert(window != (XWindowInfo *) NULL);
7619 if (window->pixmap != (Pixmap) NULL)
7622 Destroy previous X pixmap.
7624 (void) XFreePixmap(display,window->pixmap);
7625 window->pixmap=(Pixmap) NULL;
7627 if (window->use_pixmap == MagickFalse)
7628 return(MagickFalse);
7629 if (window->ximage == (XImage *) NULL)
7630 return(MagickFalse);
7632 Display busy cursor.
7634 (void) XCheckDefineCursor(display,window->id,window->busy_cursor);
7635 (void) XFlush(display);
7639 width=(unsigned int) window->ximage->width;
7640 height=(unsigned int) window->ximage->height;
7641 window->pixmap=XCreatePixmap(display,window->id,width,height,window->depth);
7642 if (window->pixmap == (Pixmap) NULL)
7645 Unable to allocate pixmap.
7647 (void) XCheckDefineCursor(display,window->id,window->cursor);
7648 return(MagickFalse);
7651 Copy X image to pixmap.
7653 #if defined(MAGICKCORE_HAVE_SHARED_MEMORY)
7654 if (window->shared_memory)
7655 (void) XShmPutImage(display,window->pixmap,window->annotate_context,
7656 window->ximage,0,0,0,0,width,height,MagickTrue);
7658 if (window->shared_memory == MagickFalse)
7659 (void) XPutImage(display,window->pixmap,window->annotate_context,
7660 window->ximage,0,0,0,0,width,height);
7661 if (IsEventLogging())
7663 (void) LogMagickEvent(X11Event,GetMagickModule(),"Pixmap:");
7664 (void) LogMagickEvent(X11Event,GetMagickModule()," width, height: %ux%u",
7670 (void) XCheckDefineCursor(display,window->id,window->cursor);
7675 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
7679 % X M a k e S t a n d a r d C o l o r m a p %
7683 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
7685 % XMakeStandardColormap() creates an X11 Standard Colormap.
7687 % The format of the XMakeStandardColormap method is:
7689 % void XMakeStandardColormap(Display *display,XVisualInfo *visual_info,
7690 % XResourceInfo *resource_info,Image *image,XStandardColormap *map_info,
7691 % XPixelInfo *pixel,ExceptionInfo *exception)
7693 % A description of each parameter follows:
7695 % o display: Specifies a connection to an X server; returned from
7698 % o visual_info: Specifies a pointer to a X11 XVisualInfo structure;
7699 % returned from XGetVisualInfo.
7701 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
7703 % o image: the image.
7705 % o map_info: If a Standard Colormap type is specified, this structure is
7706 % initialized with info from the Standard Colormap.
7708 % o pixel: Specifies a pointer to a XPixelInfo structure.
7710 % o exception: return any errors or warnings in this structure.
7714 #if defined(__cplusplus) || defined(c_plusplus)
7718 static inline MagickRealType DiversityPixelIntensity(
7719 const DiversityPacket *pixel)
7724 intensity=0.299*pixel->red+0.587*pixel->green+0.114*pixel->blue;
7728 static int IntensityCompare(const void *x,const void *y)
7737 color_1=(DiversityPacket *) x;
7738 color_2=(DiversityPacket *) y;
7739 diversity=(int) (DiversityPixelIntensity(color_2)-
7740 DiversityPixelIntensity(color_1));
7744 static int PopularityCompare(const void *x,const void *y)
7750 color_1=(DiversityPacket *) x;
7751 color_2=(DiversityPacket *) y;
7752 return((int) color_2->count-(int) color_1->count);
7755 #if defined(__cplusplus) || defined(c_plusplus)
7759 static inline Quantum ScaleXToQuantum(const size_t x,
7762 return((Quantum) (((MagickRealType) QuantumRange*x)/scale+0.5));
7765 MagickPrivate void XMakeStandardColormap(Display *display,
7766 XVisualInfo *visual_info,XResourceInfo *resource_info,Image *image,
7767 XStandardColormap *map_info,XPixelInfo *pixel,ExceptionInfo *exception)
7790 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
7791 assert(display != (Display *) NULL);
7792 assert(visual_info != (XVisualInfo *) NULL);
7793 assert(map_info != (XStandardColormap *) NULL);
7794 assert(resource_info != (XResourceInfo *) NULL);
7795 assert(pixel != (XPixelInfo *) NULL);
7796 if (resource_info->map_type != (char *) NULL)
7799 Standard Colormap is already defined (i.e. xstdcmap).
7801 XGetPixelInfo(display,visual_info,map_info,resource_info,image,
7803 number_colors=(unsigned int) (map_info->base_pixel+
7804 (map_info->red_max+1)*(map_info->green_max+1)*(map_info->blue_max+1));
7805 if ((map_info->red_max*map_info->green_max*map_info->blue_max) != 0)
7806 if ((image->matte == MagickFalse) &&
7807 (resource_info->color_recovery == MagickFalse) &&
7808 resource_info->quantize_info->dither &&
7809 (number_colors < MaxColormapSize))
7818 Improve image appearance with error diffusion.
7820 affinity_image=AcquireImage((ImageInfo *) NULL,exception);
7821 if (affinity_image == (Image *) NULL)
7822 ThrowXWindowFatalException(ResourceLimitFatalError,
7823 "UnableToDitherImage",image->filename);
7824 affinity_image->columns=number_colors;
7825 affinity_image->rows=1;
7827 Initialize colormap image.
7829 q=QueueAuthenticPixels(affinity_image,0,0,affinity_image->columns,
7831 if (q != (Quantum *) NULL)
7833 for (i=0; i < (ssize_t) number_colors; i++)
7835 SetPixelRed(affinity_image,0,q);
7836 if (map_info->red_max != 0)
7837 SetPixelRed(affinity_image,
7838 ScaleXToQuantum((size_t) (i/map_info->red_mult),
7839 map_info->red_max),q);
7840 SetPixelGreen(affinity_image,0,q);
7841 if (map_info->green_max != 0)
7842 SetPixelGreen(affinity_image,
7843 ScaleXToQuantum((size_t) ((i/map_info->green_mult) %
7844 (map_info->green_max+1)),map_info->green_max),q);
7845 SetPixelBlue(affinity_image,0,q);
7846 if (map_info->blue_max != 0)
7847 SetPixelBlue(affinity_image,
7848 ScaleXToQuantum((size_t) (i % map_info->green_mult),
7849 map_info->blue_max),q);
7850 SetPixelAlpha(affinity_image,
7851 TransparentAlpha,q);
7852 q+=GetPixelChannels(affinity_image);
7854 (void) SyncAuthenticPixels(affinity_image,exception);
7855 (void) RemapImage(resource_info->quantize_info,image,
7856 affinity_image,exception);
7858 XGetPixelInfo(display,visual_info,map_info,resource_info,image,
7860 (void) SetImageStorageClass(image,DirectClass,exception);
7861 affinity_image=DestroyImage(affinity_image);
7863 if (IsEventLogging())
7865 (void) LogMagickEvent(X11Event,GetMagickModule(),
7866 "Standard Colormap:");
7867 (void) LogMagickEvent(X11Event,GetMagickModule(),
7868 " colormap id: 0x%lx",map_info->colormap);
7869 (void) LogMagickEvent(X11Event,GetMagickModule(),
7870 " red, green, blue max: %lu %lu %lu",map_info->red_max,
7871 map_info->green_max,map_info->blue_max);
7872 (void) LogMagickEvent(X11Event,GetMagickModule(),
7873 " red, green, blue mult: %lu %lu %lu",map_info->red_mult,
7874 map_info->green_mult,map_info->blue_mult);
7878 if ((visual_info->klass != DirectColor) &&
7879 (visual_info->klass != TrueColor))
7880 if ((image->storage_class == DirectClass) ||
7881 ((int) image->colors > visual_info->colormap_size))
7887 Image has more colors than the visual supports.
7889 quantize_info=(*resource_info->quantize_info);
7890 quantize_info.number_colors=(size_t) visual_info->colormap_size;
7891 (void) QuantizeImage(&quantize_info,image,exception);
7894 Free previous and create new colormap.
7896 (void) XFreeStandardColormap(display,visual_info,map_info,pixel);
7897 colormap=XDefaultColormap(display,visual_info->screen);
7898 if (visual_info->visual != XDefaultVisual(display,visual_info->screen))
7899 colormap=XCreateColormap(display,XRootWindow(display,visual_info->screen),
7900 visual_info->visual,visual_info->klass == DirectColor ?
7901 AllocAll : AllocNone);
7902 if (colormap == (Colormap) NULL)
7903 ThrowXWindowFatalException(ResourceLimitFatalError,"UnableToCreateColormap",
7906 Initialize the map and pixel info structures.
7908 XGetMapInfo(visual_info,colormap,map_info);
7909 XGetPixelInfo(display,visual_info,map_info,resource_info,image,pixel);
7911 Allocating colors in server colormap is based on visual class.
7913 switch (visual_info->klass)
7919 Define Standard Colormap for StaticGray or StaticColor visual.
7921 number_colors=image->colors;
7922 colors=(XColor *) AcquireQuantumMemory((size_t)
7923 visual_info->colormap_size,sizeof(*colors));
7924 if (colors == (XColor *) NULL)
7925 ThrowXWindowFatalException(ResourceLimitFatalError,
7926 "UnableToCreateColormap",image->filename);
7928 color.flags=(char) (DoRed | DoGreen | DoBlue);
7929 for (i=0; i < (ssize_t) image->colors; i++)
7931 color.red=ScaleQuantumToShort(XRedGamma(image->colormap[i].red));
7932 color.green=ScaleQuantumToShort(XGreenGamma(image->colormap[i].green));
7933 color.blue=ScaleQuantumToShort(XBlueGamma(image->colormap[i].blue));
7934 if (visual_info->klass != StaticColor)
7936 gray_value=(unsigned short) XPixelIntensity(&color);
7937 color.red=gray_value;
7938 color.green=gray_value;
7939 color.blue=gray_value;
7941 status=XAllocColor(display,colormap,&color);
7942 if (status == False)
7944 colormap=XCopyColormapAndFree(display,colormap);
7945 (void) XAllocColor(display,colormap,&color);
7947 pixel->pixels[i]=color.pixel;
7959 Define Standard Colormap for GrayScale or PseudoColor visual.
7961 number_colors=image->colors;
7962 colors=(XColor *) AcquireQuantumMemory((size_t)
7963 visual_info->colormap_size,sizeof(*colors));
7964 if (colors == (XColor *) NULL)
7965 ThrowXWindowFatalException(ResourceLimitFatalError,
7966 "UnableToCreateColormap",image->filename);
7968 Preallocate our GUI colors.
7970 (void) XAllocColor(display,colormap,&pixel->foreground_color);
7971 (void) XAllocColor(display,colormap,&pixel->background_color);
7972 (void) XAllocColor(display,colormap,&pixel->border_color);
7973 (void) XAllocColor(display,colormap,&pixel->matte_color);
7974 (void) XAllocColor(display,colormap,&pixel->highlight_color);
7975 (void) XAllocColor(display,colormap,&pixel->shadow_color);
7976 (void) XAllocColor(display,colormap,&pixel->depth_color);
7977 (void) XAllocColor(display,colormap,&pixel->trough_color);
7978 for (i=0; i < MaxNumberPens; i++)
7979 (void) XAllocColor(display,colormap,&pixel->pen_colors[i]);
7981 Determine if image colors will "fit" into X server colormap.
7983 colormap_type=resource_info->colormap;
7984 status=XAllocColorCells(display,colormap,MagickFalse,(unsigned long *)
7985 NULL,0,pixel->pixels,(unsigned int) image->colors);
7986 if (status != False)
7987 colormap_type=PrivateColormap;
7988 if (colormap_type == SharedColormap)
8009 Define Standard colormap for shared GrayScale or PseudoColor visual.
8011 diversity=(DiversityPacket *) AcquireQuantumMemory(image->colors,
8012 sizeof(*diversity));
8013 if (diversity == (DiversityPacket *) NULL)
8014 ThrowXWindowFatalException(ResourceLimitFatalError,
8015 "UnableToCreateColormap",image->filename);
8016 for (i=0; i < (ssize_t) image->colors; i++)
8018 diversity[i].red=ClampToQuantum(image->colormap[i].red);
8019 diversity[i].green=ClampToQuantum(image->colormap[i].green);
8020 diversity[i].blue=ClampToQuantum(image->colormap[i].blue);
8021 diversity[i].index=(unsigned short) i;
8022 diversity[i].count=0;
8024 image_view=AcquireCacheView(image);
8025 for (y=0; y < (int) image->rows; y++)
8030 register const Quantum
8033 p=GetCacheViewAuthenticPixels(image_view,0,(ssize_t) y,
8034 image->columns,1,exception);
8035 if (p == (const Quantum *) NULL)
8037 for (x=(int) image->columns-1; x >= 0; x--)
8039 diversity[(ssize_t) GetPixelIndex(image,p)].count++;
8040 p+=GetPixelChannels(image);
8043 image_view=DestroyCacheView(image_view);
8045 Sort colors by decreasing intensity.
8047 qsort((void *) diversity,image->colors,sizeof(*diversity),
8049 for (i=0; i < (ssize_t) image->colors; )
8051 diversity[i].count<<=4; /* increase this colors popularity */
8052 i+=MagickMax((int) (image->colors >> 4),2);
8054 diversity[image->colors-1].count<<=4;
8055 qsort((void *) diversity,image->colors,sizeof(*diversity),
8061 color.flags=(char) (DoRed | DoGreen | DoBlue);
8062 for (i=0; i < (ssize_t) image->colors; i++)
8064 index=diversity[i].index;
8066 ScaleQuantumToShort(XRedGamma(image->colormap[index].red));
8068 ScaleQuantumToShort(XGreenGamma(image->colormap[index].green));
8070 ScaleQuantumToShort(XBlueGamma(image->colormap[index].blue));
8071 if (visual_info->klass != PseudoColor)
8073 gray_value=(unsigned short) XPixelIntensity(&color);
8074 color.red=gray_value;
8075 color.green=gray_value;
8076 color.blue=gray_value;
8078 status=XAllocColor(display,colormap,&color);
8079 if (status == False)
8081 pixel->pixels[index]=color.pixel;
8085 Read X server colormap.
8087 server_colors=(XColor *) AcquireQuantumMemory((size_t)
8088 visual_info->colormap_size,sizeof(*server_colors));
8089 if (server_colors == (XColor *) NULL)
8090 ThrowXWindowFatalException(ResourceLimitFatalError,
8091 "UnableToCreateColormap",image->filename);
8092 for (x=visual_info->colormap_size-1; x >= 0; x--)
8093 server_colors[x].pixel=(size_t) x;
8094 (void) XQueryColors(display,colormap,server_colors,
8095 (int) MagickMin((unsigned int) visual_info->colormap_size,256));
8097 Select remaining colors from X server colormap.
8099 for (; i < (ssize_t) image->colors; i++)
8101 index=diversity[i].index;
8103 ScaleQuantumToShort(XRedGamma(image->colormap[index].red));
8105 ScaleQuantumToShort(XGreenGamma(image->colormap[index].green));
8107 ScaleQuantumToShort(XBlueGamma(image->colormap[index].blue));
8108 if (visual_info->klass != PseudoColor)
8110 gray_value=(unsigned short) XPixelIntensity(&color);
8111 color.red=gray_value;
8112 color.green=gray_value;
8113 color.blue=gray_value;
8115 XBestPixel(display,colormap,server_colors,(unsigned int)
8116 visual_info->colormap_size,&color);
8117 pixel->pixels[index]=color.pixel;
8120 if ((int) image->colors < visual_info->colormap_size)
8123 Fill up colors array-- more choices for pen colors.
8125 retain_colors=MagickMin((unsigned int)
8126 (visual_info->colormap_size-image->colors),256);
8127 for (i=0; i < (ssize_t) retain_colors; i++)
8128 *p++=server_colors[i];
8129 number_colors+=retain_colors;
8131 server_colors=(XColor *) RelinquishMagickMemory(server_colors);
8132 diversity=(DiversityPacket *) RelinquishMagickMemory(diversity);
8136 Define Standard colormap for private GrayScale or PseudoColor visual.
8138 if (status == False)
8141 Not enough colormap entries in the colormap-- Create a new colormap.
8143 colormap=XCreateColormap(display,
8144 XRootWindow(display,visual_info->screen),visual_info->visual,
8146 if (colormap == (Colormap) NULL)
8147 ThrowXWindowFatalException(ResourceLimitFatalError,
8148 "UnableToCreateColormap",image->filename);
8149 map_info->colormap=colormap;
8150 if ((int) image->colors < visual_info->colormap_size)
8153 Retain colors from the default colormap to help lessens the
8154 effects of colormap flashing.
8156 retain_colors=MagickMin((unsigned int)
8157 (visual_info->colormap_size-image->colors),256);
8158 p=colors+image->colors;
8159 for (i=0; i < (ssize_t) retain_colors; i++)
8161 p->pixel=(unsigned long) i;
8164 (void) XQueryColors(display,
8165 XDefaultColormap(display,visual_info->screen),
8166 colors+image->colors,(int) retain_colors);
8168 Transfer colors from default to private colormap.
8170 (void) XAllocColorCells(display,colormap,MagickFalse,
8171 (unsigned long *) NULL,0,pixel->pixels,(unsigned int)
8173 p=colors+image->colors;
8174 for (i=0; i < (ssize_t) retain_colors; i++)
8176 p->pixel=pixel->pixels[i];
8179 (void) XStoreColors(display,colormap,colors+image->colors,
8180 (int) retain_colors);
8181 number_colors+=retain_colors;
8183 (void) XAllocColorCells(display,colormap,MagickFalse,
8184 (unsigned long *) NULL,0,pixel->pixels,(unsigned int)
8188 Store the image colormap.
8191 color.flags=(char) (DoRed | DoGreen | DoBlue);
8192 for (i=0; i < (ssize_t) image->colors; i++)
8194 color.red=ScaleQuantumToShort(XRedGamma(image->colormap[i].red));
8195 color.green=ScaleQuantumToShort(XGreenGamma(image->colormap[i].green));
8196 color.blue=ScaleQuantumToShort(XBlueGamma(image->colormap[i].blue));
8197 if (visual_info->klass != PseudoColor)
8199 gray_value=(unsigned short) XPixelIntensity(&color);
8200 color.red=gray_value;
8201 color.green=gray_value;
8202 color.blue=gray_value;
8204 color.pixel=pixel->pixels[i];
8207 (void) XStoreColors(display,colormap,colors,(int) image->colors);
8218 Define Standard Colormap for TrueColor or DirectColor visual.
8220 number_colors=(unsigned int) ((map_info->red_max*map_info->red_mult)+
8221 (map_info->green_max*map_info->green_mult)+
8222 (map_info->blue_max*map_info->blue_mult)+1);
8223 linear_colormap=(number_colors > 4096) ||
8224 (((int) (map_info->red_max+1) == visual_info->colormap_size) &&
8225 ((int) (map_info->green_max+1) == visual_info->colormap_size) &&
8226 ((int) (map_info->blue_max+1) == visual_info->colormap_size)) ?
8227 MagickTrue : MagickFalse;
8228 if (linear_colormap != MagickFalse)
8229 number_colors=(size_t) visual_info->colormap_size;
8231 Allocate color array.
8233 colors=(XColor *) AcquireQuantumMemory(number_colors,sizeof(*colors));
8234 if (colors == (XColor *) NULL)
8235 ThrowXWindowFatalException(ResourceLimitFatalError,
8236 "UnableToCreateColormap",image->filename);
8238 Initialize linear color ramp.
8241 color.flags=(char) (DoRed | DoGreen | DoBlue);
8242 if (linear_colormap != MagickFalse)
8243 for (i=0; i < (ssize_t) number_colors; i++)
8245 color.blue=(unsigned short) 0;
8246 if (map_info->blue_max != 0)
8247 color.blue=(unsigned short) ((size_t)
8248 ((65535L*(i % map_info->green_mult))/map_info->blue_max));
8249 color.green=color.blue;
8250 color.red=color.blue;
8251 color.pixel=XStandardPixel(map_info,&color);
8255 for (i=0; i < (ssize_t) number_colors; i++)
8257 color.red=(unsigned short) 0;
8258 if (map_info->red_max != 0)
8259 color.red=(unsigned short) ((size_t)
8260 ((65535L*(i/map_info->red_mult))/map_info->red_max));
8261 color.green=(unsigned int) 0;
8262 if (map_info->green_max != 0)
8263 color.green=(unsigned short) ((size_t)
8264 ((65535L*((i/map_info->green_mult) % (map_info->green_max+1)))/
8265 map_info->green_max));
8266 color.blue=(unsigned short) 0;
8267 if (map_info->blue_max != 0)
8268 color.blue=(unsigned short) ((size_t)
8269 ((65535L*(i % map_info->green_mult))/map_info->blue_max));
8270 color.pixel=XStandardPixel(map_info,&color);
8273 if ((visual_info->klass == DirectColor) &&
8274 (colormap != XDefaultColormap(display,visual_info->screen)))
8275 (void) XStoreColors(display,colormap,colors,(int) number_colors);
8277 for (i=0; i < (ssize_t) number_colors; i++)
8278 (void) XAllocColor(display,colormap,&colors[i]);
8282 if ((visual_info->klass != DirectColor) &&
8283 (visual_info->klass != TrueColor))
8286 Set foreground, background, border, etc. pixels.
8288 XBestPixel(display,colormap,colors,(unsigned int) number_colors,
8289 &pixel->foreground_color);
8290 XBestPixel(display,colormap,colors,(unsigned int) number_colors,
8291 &pixel->background_color);
8292 if (pixel->background_color.pixel == pixel->foreground_color.pixel)
8295 Foreground and background colors must differ.
8297 pixel->background_color.red=(~pixel->foreground_color.red);
8298 pixel->background_color.green=
8299 (~pixel->foreground_color.green);
8300 pixel->background_color.blue=
8301 (~pixel->foreground_color.blue);
8302 XBestPixel(display,colormap,colors,(unsigned int) number_colors,
8303 &pixel->background_color);
8305 XBestPixel(display,colormap,colors,(unsigned int) number_colors,
8306 &pixel->border_color);
8307 XBestPixel(display,colormap,colors,(unsigned int) number_colors,
8308 &pixel->matte_color);
8309 XBestPixel(display,colormap,colors,(unsigned int) number_colors,
8310 &pixel->highlight_color);
8311 XBestPixel(display,colormap,colors,(unsigned int) number_colors,
8312 &pixel->shadow_color);
8313 XBestPixel(display,colormap,colors,(unsigned int) number_colors,
8314 &pixel->depth_color);
8315 XBestPixel(display,colormap,colors,(unsigned int) number_colors,
8316 &pixel->trough_color);
8317 for (i=0; i < MaxNumberPens; i++)
8319 XBestPixel(display,colormap,colors,(unsigned int) number_colors,
8320 &pixel->pen_colors[i]);
8321 pixel->pixels[image->colors+i]=pixel->pen_colors[i].pixel;
8323 pixel->colors=(ssize_t) (image->colors+MaxNumberPens);
8325 colors=(XColor *) RelinquishMagickMemory(colors);
8326 if (IsEventLogging())
8328 (void) LogMagickEvent(X11Event,GetMagickModule(),"Standard Colormap:");
8329 (void) LogMagickEvent(X11Event,GetMagickModule()," colormap id: 0x%lx",
8330 map_info->colormap);
8331 (void) LogMagickEvent(X11Event,GetMagickModule(),
8332 " red, green, blue max: %lu %lu %lu",map_info->red_max,
8333 map_info->green_max,map_info->blue_max);
8334 (void) LogMagickEvent(X11Event,GetMagickModule(),
8335 " red, green, blue mult: %lu %lu %lu",map_info->red_mult,
8336 map_info->green_mult,map_info->blue_mult);
8341 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8345 % X M a k e W i n d o w %
8349 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8351 % XMakeWindow() creates an X11 window.
8353 % The format of the XMakeWindow method is:
8355 % void XMakeWindow(Display *display,Window parent,char **argv,int argc,
8356 % XClassHint *class_hint,XWMHints *manager_hints,
8357 % XWindowInfo *window_info)
8359 % A description of each parameter follows:
8361 % o display: Specifies a connection to an X server; returned from
8364 % o parent: Specifies the parent window_info.
8366 % o argv: Specifies the application's argument list.
8368 % o argc: Specifies the number of arguments.
8370 % o class_hint: Specifies a pointer to a X11 XClassHint structure.
8372 % o manager_hints: Specifies a pointer to a X11 XWMHints structure.
8374 % o window_info: Specifies a pointer to a X11 XWindowInfo structure.
8377 MagickPrivate void XMakeWindow(Display *display,Window parent,char **argv,
8378 int argc,XClassHint *class_hint,XWMHints *manager_hints,
8379 XWindowInfo *window_info)
8381 #define MinWindowSize 64
8389 static XTextProperty
8400 Set window info hints.
8402 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
8403 assert(display != (Display *) NULL);
8404 assert(window_info != (XWindowInfo *) NULL);
8405 size_hints=XAllocSizeHints();
8406 if (size_hints == (XSizeHints *) NULL)
8407 ThrowXWindowFatalException(XServerFatalError,"UnableToMakeXWindow",argv[0]);
8408 size_hints->flags=(int) window_info->flags;
8409 size_hints->x=window_info->x;
8410 size_hints->y=window_info->y;
8411 size_hints->width=(int) window_info->width;
8412 size_hints->height=(int) window_info->height;
8413 if (window_info->immutable != MagickFalse)
8416 Window size cannot be changed.
8418 size_hints->min_width=size_hints->width;
8419 size_hints->min_height=size_hints->height;
8420 size_hints->max_width=size_hints->width;
8421 size_hints->max_height=size_hints->height;
8422 size_hints->flags|=PMinSize;
8423 size_hints->flags|=PMaxSize;
8428 Window size can be changed.
8430 size_hints->min_width=(int) window_info->min_width;
8431 size_hints->min_height=(int) window_info->min_height;
8432 size_hints->flags|=PResizeInc;
8433 size_hints->width_inc=(int) window_info->width_inc;
8434 size_hints->height_inc=(int) window_info->height_inc;
8435 #if !defined(PRE_R4_ICCCM)
8436 size_hints->flags|=PBaseSize;
8437 size_hints->base_width=size_hints->width_inc;
8438 size_hints->base_height=size_hints->height_inc;
8441 gravity=NorthWestGravity;
8442 if (window_info->geometry != (char *) NULL)
8445 default_geometry[MaxTextExtent],
8446 geometry[MaxTextExtent];
8455 User specified geometry.
8457 (void) FormatLocaleString(default_geometry,MaxTextExtent,"%dx%d",
8458 size_hints->width,size_hints->height);
8459 (void) CopyMagickString(geometry,window_info->geometry,MaxTextExtent);
8461 while (strlen(p) != 0)
8463 if ((isspace((int) ((unsigned char) *p)) == 0) && (*p != '%'))
8466 (void) CopyMagickString(p,p+1,MaxTextExtent);
8468 flags=XWMGeometry(display,window_info->screen,geometry,default_geometry,
8469 window_info->border_width,size_hints,&size_hints->x,&size_hints->y,
8470 &size_hints->width,&size_hints->height,&gravity);
8471 if ((flags & WidthValue) && (flags & HeightValue))
8472 size_hints->flags|=USSize;
8473 if ((flags & XValue) && (flags & YValue))
8475 size_hints->flags|=USPosition;
8476 window_info->x=size_hints->x;
8477 window_info->y=size_hints->y;
8480 #if !defined(PRE_R4_ICCCM)
8481 size_hints->win_gravity=gravity;
8482 size_hints->flags|=PWinGravity;
8484 if (window_info->id == (Window) NULL)
8485 window_info->id=XCreateWindow(display,parent,window_info->x,window_info->y,
8486 (unsigned int) size_hints->width,(unsigned int) size_hints->height,
8487 window_info->border_width,(int) window_info->depth,InputOutput,
8488 window_info->visual,(unsigned long) window_info->mask,
8489 &window_info->attributes);
8502 Window already exists; change relevant attributes.
8504 (void) XChangeWindowAttributes(display,window_info->id,(unsigned long)
8505 window_info->mask,&window_info->attributes);
8506 mask=ConfigureNotify;
8507 while (XCheckTypedWindowEvent(display,window_info->id,(int) mask,&sans_event)) ;
8508 window_changes.x=window_info->x;
8509 window_changes.y=window_info->y;
8510 window_changes.width=(int) window_info->width;
8511 window_changes.height=(int) window_info->height;
8512 mask=(MagickStatusType) (CWWidth | CWHeight);
8513 if (window_info->flags & USPosition)
8515 (void) XReconfigureWMWindow(display,window_info->id,window_info->screen,
8516 mask,&window_changes);
8518 if (window_info->id == (Window) NULL)
8519 ThrowXWindowFatalException(XServerFatalError,"UnableToCreateWindow",
8521 status=XStringListToTextProperty(&window_info->name,1,&window_name);
8522 if (status == False)
8523 ThrowXWindowFatalException(XServerFatalError,"UnableToCreateTextProperty",
8525 status=XStringListToTextProperty(&window_info->icon_name,1,&icon_name);
8526 if (status == False)
8527 ThrowXWindowFatalException(XServerFatalError,"UnableToCreateTextProperty",
8528 window_info->icon_name);
8529 if (window_info->icon_geometry != (char *) NULL)
8537 User specified icon geometry.
8539 size_hints->flags|=USPosition;
8540 flags=XWMGeometry(display,window_info->screen,window_info->icon_geometry,
8541 (char *) NULL,0,size_hints,&manager_hints->icon_x,
8542 &manager_hints->icon_y,&width,&height,&gravity);
8543 if ((flags & XValue) && (flags & YValue))
8544 manager_hints->flags|=IconPositionHint;
8546 XSetWMProperties(display,window_info->id,&window_name,&icon_name,argv,argc,
8547 size_hints,manager_hints,class_hint);
8548 if (window_name.value != (void *) NULL)
8550 (void) XFree((void *) window_name.value);
8551 window_name.value=(unsigned char *) NULL;
8552 window_name.nitems=0;
8554 if (icon_name.value != (void *) NULL)
8556 (void) XFree((void *) icon_name.value);
8557 icon_name.value=(unsigned char *) NULL;
8560 atom_list[0]=XInternAtom(display,"WM_DELETE_WINDOW",MagickFalse);
8561 atom_list[1]=XInternAtom(display,"WM_TAKE_FOCUS",MagickFalse);
8562 (void) XSetWMProtocols(display,window_info->id,atom_list,2);
8563 (void) XFree((void *) size_hints);
8564 if (window_info->shape != MagickFalse)
8566 #if defined(MAGICKCORE_HAVE_SHAPE)
8572 Can we apply a non-rectangular shaping mask?
8576 if (XShapeQueryExtension(display,&error_base,&event_base) == 0)
8577 window_info->shape=MagickFalse;
8579 window_info->shape=MagickFalse;
8582 if (window_info->shared_memory)
8584 #if defined(MAGICKCORE_HAVE_SHARED_MEMORY)
8586 Can we use shared memory with this window?
8588 if (XShmQueryExtension(display) == 0)
8589 window_info->shared_memory=MagickFalse;
8591 window_info->shared_memory=MagickFalse;
8594 window_info->image=NewImageList();
8595 window_info->destroy=MagickFalse;
8599 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8603 % X M a g i c k P r o g r e s s M o n i t o r %
8607 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8609 % XMagickProgressMonitor() displays the progress a task is making in
8610 % completing a task.
8612 % The format of the XMagickProgressMonitor method is:
8614 % void XMagickProgressMonitor(const char *task,
8615 % const MagickOffsetType quantum,const MagickSizeType span,
8616 % void *client_data)
8618 % A description of each parameter follows:
8620 % o task: Identifies the task in progress.
8622 % o quantum: Specifies the quantum position within the span which represents
8623 % how much progress has been made in completing a task.
8625 % o span: Specifies the span relative to completing a task.
8627 % o client_data: Pointer to any client data.
8631 static const char *GetLocaleMonitorMessage(const char *text)
8634 message[MaxTextExtent],
8643 (void) CopyMagickMemory(tag,text,MaxTextExtent);
8645 if (p != (char *) NULL)
8647 (void) FormatLocaleString(message,MaxTextExtent,"Monitor/%s",tag);
8648 locale_message=GetLocaleMessage(message);
8649 if (locale_message == message)
8651 return(locale_message);
8654 MagickPrivate MagickBooleanType XMagickProgressMonitor(const char *tag,
8655 const MagickOffsetType quantum,const MagickSizeType span,
8656 void *magick_unused(client_data))
8661 windows=XSetWindows((XWindows *) ~0);
8662 if (windows == (XWindows *) NULL)
8664 if (windows->info.mapped != MagickFalse)
8665 XProgressMonitorWidget(windows->display,windows,
8666 GetLocaleMonitorMessage(tag),quantum,span);
8671 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8675 % X Q u e r y C o l o r D a t a b a s e %
8679 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8681 % XQueryColorCompliance() looks up a RGB values for a color given in the target
8684 % The format of the XQueryColorDatabase method is:
8686 % MagickBooleanType XQueryColorCompliance(const char *target,XColor *color)
8688 % A description of each parameter follows:
8690 % o target: Specifies the color to lookup in the X color database.
8692 % o color: A pointer to an PixelInfo structure. The RGB value of the target
8693 % color is returned as this value.
8696 MagickPrivate MagickBooleanType XQueryColorCompliance(const char *target,
8703 *display = (Display *) NULL;
8712 Initialize color return value.
8714 assert(color != (XColor *) NULL);
8718 color->flags=(char) (DoRed | DoGreen | DoBlue);
8719 if ((target == (char *) NULL) || (*target == '\0'))
8720 target="#ffffffffffff";
8722 Let the X server define the color for us.
8724 if (display == (Display *) NULL)
8725 display=XOpenDisplay((char *) NULL);
8726 if (display == (Display *) NULL)
8728 ThrowXWindowFatalException(XServerError,"ColorIsNotKnownToServer",target);
8729 return(MagickFalse);
8731 colormap=XDefaultColormap(display,XDefaultScreen(display));
8732 status=XParseColor(display,colormap,(char *) target,&xcolor);
8733 if (status == False)
8734 ThrowXWindowFatalException(XServerError,"ColorIsNotKnownToServer",target)
8737 color->red=xcolor.red;
8738 color->green=xcolor.green;
8739 color->blue=xcolor.blue;
8740 color->flags=xcolor.flags;
8742 return(status != False ? MagickTrue : MagickFalse);
8746 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8750 % X Q u e r y P o s i t i o n %
8754 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8756 % XQueryPosition() gets the pointer coordinates relative to a window.
8758 % The format of the XQueryPosition method is:
8760 % void XQueryPosition(Display *display,const Window window,int *x,int *y)
8762 % A description of each parameter follows:
8764 % o display: Specifies a connection to an X server; returned from
8767 % o window: Specifies a pointer to a Window.
8769 % o x: Return the x coordinate of the pointer relative to the origin of the
8772 % o y: Return the y coordinate of the pointer relative to the origin of the
8776 MagickPrivate void XQueryPosition(Display *display,const Window window,int *x,int *y)
8788 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
8789 assert(display != (Display *) NULL);
8790 assert(window != (Window) NULL);
8791 assert(x != (int *) NULL);
8792 assert(y != (int *) NULL);
8793 (void) XQueryPointer(display,window,&root_window,&root_window,&x_root,&y_root,
8798 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8802 % X R e f r e s h W i n d o w %
8806 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8808 % XRefreshWindow() refreshes an image in a X window.
8810 % The format of the XRefreshWindow method is:
8812 % void XRefreshWindow(Display *display,const XWindowInfo *window,
8813 % const XEvent *event)
8815 % A description of each parameter follows:
8817 % o display: Specifies a connection to an X server; returned from
8820 % o window: Specifies a pointer to a XWindowInfo structure.
8822 % o event: Specifies a pointer to a XEvent structure. If it is NULL,
8823 % the entire image is refreshed.
8826 MagickPrivate void XRefreshWindow(Display *display,const XWindowInfo *window,
8827 const XEvent *event)
8837 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
8838 assert(display != (Display *) NULL);
8839 assert(window != (XWindowInfo *) NULL);
8840 if (window->ximage == (XImage *) NULL)
8842 if (event != (XEvent *) NULL)
8845 Determine geometry from expose event.
8849 width=(unsigned int) event->xexpose.width;
8850 height=(unsigned int) event->xexpose.height;
8858 Refresh entire window; discard outstanding expose events.
8862 width=window->width;
8863 height=window->height;
8864 while (XCheckTypedWindowEvent(display,window->id,Expose,&sans_event)) ;
8865 if (window->matte_pixmap != (Pixmap) NULL)
8867 #if defined(MAGICKCORE_HAVE_SHAPE)
8868 if (window->shape != MagickFalse)
8869 XShapeCombineMask(display,window->id,ShapeBounding,0,0,
8870 window->matte_pixmap,ShapeSet);
8875 Check boundary conditions.
8877 if ((window->ximage->width-(x+window->x)) < (int) width)
8878 width=(unsigned int) (window->ximage->width-(x+window->x));
8879 if ((window->ximage->height-(y+window->y)) < (int) height)
8880 height=(unsigned int) (window->ximage->height-(y+window->y));
8884 if (window->matte_pixmap != (Pixmap) NULL)
8885 (void) XSetClipMask(display,window->annotate_context,window->matte_pixmap);
8886 if (window->pixmap != (Pixmap) NULL)
8888 if (window->depth > 1)
8889 (void) XCopyArea(display,window->pixmap,window->id,
8890 window->annotate_context,x+window->x,y+window->y,width,height,x,y);
8892 (void) XCopyPlane(display,window->pixmap,window->id,
8893 window->highlight_context,x+window->x,y+window->y,width,height,x,y,
8898 #if defined(MAGICKCORE_HAVE_SHARED_MEMORY)
8899 if (window->shared_memory)
8900 (void) XShmPutImage(display,window->id,window->annotate_context,
8901 window->ximage,x+window->x,y+window->y,x,y,width,height,MagickTrue);
8903 if (window->shared_memory == MagickFalse)
8904 (void) XPutImage(display,window->id,window->annotate_context,
8905 window->ximage,x+window->x,y+window->y,x,y,width,height);
8907 if (window->matte_pixmap != (Pixmap) NULL)
8908 (void) XSetClipMask(display,window->annotate_context,None);
8909 (void) XFlush(display);
8913 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8917 % X R e m o t e C o m m a n d %
8921 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8923 % XRemoteCommand() forces a remote display(1) to display the specified
8926 % The format of the XRemoteCommand method is:
8928 % MagickBooleanType XRemoteCommand(Display *display,const char *window,
8929 % const char *filename)
8931 % A description of each parameter follows:
8933 % o display: Specifies a connection to an X server; returned from
8936 % o window: Specifies the name or id of an X window.
8938 % o filename: the name of the image filename to display.
8941 MagickExport MagickBooleanType XRemoteCommand(Display *display,
8942 const char *window,const char *filename)
8951 assert(filename != (char *) NULL);
8952 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",filename);
8953 if (display == (Display *) NULL)
8954 display=XOpenDisplay((char *) NULL);
8955 if (display == (Display *) NULL)
8957 ThrowXWindowException(XServerError,"UnableToOpenXServer",filename);
8958 return(MagickFalse);
8960 remote_atom=XInternAtom(display,"IM_PROTOCOLS",MagickFalse);
8961 remote_window=(Window) NULL;
8962 root_window=XRootWindow(display,XDefaultScreen(display));
8963 if (window != (char *) NULL)
8966 Search window hierarchy and identify any clients by name or ID.
8968 if (isdigit((unsigned char) *window) != 0)
8969 remote_window=XWindowByID(display,root_window,(Window)
8970 strtol((char *) window,(char **) NULL,0));
8971 if (remote_window == (Window) NULL)
8972 remote_window=XWindowByName(display,root_window,window);
8974 if (remote_window == (Window) NULL)
8975 remote_window=XWindowByProperty(display,root_window,remote_atom);
8976 if (remote_window == (Window) NULL)
8978 ThrowXWindowException(XServerError,"UnableToConnectToRemoteDisplay",
8980 return(MagickFalse);
8983 Send remote command.
8985 remote_atom=XInternAtom(display,"IM_REMOTE_COMMAND",MagickFalse);
8986 (void) XChangeProperty(display,remote_window,remote_atom,XA_STRING,8,
8987 PropModeReplace,(unsigned char *) filename,(int) strlen(filename));
8988 (void) XSync(display,MagickFalse);
8993 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8997 % X R e t a i n W i n d o w C o l o r s %
9001 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9003 % XRetainWindowColors() sets X11 color resources on a window. This preserves
9004 % the colors associated with an image displayed on the window.
9006 % The format of the XRetainWindowColors method is:
9008 % void XRetainWindowColors(Display *display,const Window window)
9010 % A description of each parameter follows:
9012 % o display: Specifies a connection to an X server; returned from
9015 % o window: Specifies a pointer to a XWindowInfo structure.
9018 MagickExport void XRetainWindowColors(Display *display,const Window window)
9027 Put property on the window.
9029 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
9030 assert(display != (Display *) NULL);
9031 assert(window != (Window) NULL);
9032 property=XInternAtom(display,"_XSETROOT_ID",MagickFalse);
9033 if (property == (Atom) NULL)
9035 ThrowXWindowFatalException(XServerError,"UnableToCreateProperty",
9039 pixmap=XCreatePixmap(display,window,1,1,1);
9040 if (pixmap == (Pixmap) NULL)
9042 ThrowXWindowFatalException(XServerError,"UnableToCreateBitmap","");
9045 (void) XChangeProperty(display,window,property,XA_PIXMAP,32,PropModeReplace,
9046 (unsigned char *) &pixmap,1);
9047 (void) XSetCloseDownMode(display,RetainPermanent);
9051 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9055 % X S e l e c t W i n d o w %
9059 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9061 % XSelectWindow() allows a user to select a window using the mouse. If the
9062 % mouse moves, a cropping rectangle is drawn and the extents of the rectangle
9063 % is returned in the crop_info structure.
9065 % The format of the XSelectWindow function is:
9067 % target_window=XSelectWindow(display,crop_info)
9069 % A description of each parameter follows:
9071 % o window: XSelectWindow returns the window id.
9073 % o display: Specifies a pointer to the Display structure; returned from
9076 % o crop_info: Specifies a pointer to a RectangleInfo structure. It
9077 % contains the extents of any cropping rectangle.
9080 static Window XSelectWindow(Display *display,RectangleInfo *crop_info)
9082 #define MinimumCropArea (unsigned int) 9
9109 Initialize graphic context.
9111 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
9112 assert(display != (Display *) NULL);
9113 assert(crop_info != (RectangleInfo *) NULL);
9114 root_window=XRootWindow(display,XDefaultScreen(display));
9115 context_values.background=XBlackPixel(display,XDefaultScreen(display));
9116 context_values.foreground=XWhitePixel(display,XDefaultScreen(display));
9117 context_values.function=GXinvert;
9118 context_values.plane_mask=
9119 context_values.background ^ context_values.foreground;
9120 context_values.subwindow_mode=IncludeInferiors;
9121 annotate_context=XCreateGC(display,root_window,(size_t) (GCBackground |
9122 GCForeground | GCFunction | GCSubwindowMode),&context_values);
9123 if (annotate_context == (GC) NULL)
9124 return(MagickFalse);
9126 Grab the pointer using target cursor.
9128 target_cursor=XMakeCursor(display,root_window,XDefaultColormap(display,
9129 XDefaultScreen(display)),(char * ) "white",(char * ) "black");
9130 status=XGrabPointer(display,root_window,MagickFalse,(unsigned int)
9131 (ButtonPressMask | ButtonReleaseMask | ButtonMotionMask),GrabModeSync,
9132 GrabModeAsync,root_window,target_cursor,CurrentTime);
9133 if (status != GrabSuccess)
9135 ThrowXWindowFatalException(XServerError,"UnableToGrabMouse","");
9136 return((Window) NULL);
9142 crop_info->height=0;
9144 target_window=(Window) NULL;
9149 if ((crop_info->width*crop_info->height) >= MinimumCropArea)
9150 (void) XDrawRectangle(display,root_window,annotate_context,
9151 (int) crop_info->x,(int) crop_info->y,(unsigned int) crop_info->width-1,
9152 (unsigned int) crop_info->height-1);
9154 Allow another event.
9156 (void) XAllowEvents(display,SyncPointer,CurrentTime);
9157 (void) XWindowEvent(display,root_window,ButtonPressMask |
9158 ButtonReleaseMask | ButtonMotionMask,&event);
9159 if ((crop_info->width*crop_info->height) >= MinimumCropArea)
9160 (void) XDrawRectangle(display,root_window,annotate_context,
9161 (int) crop_info->x,(int) crop_info->y,(unsigned int) crop_info->width-1,
9162 (unsigned int) crop_info->height-1);
9167 target_window=XGetSubwindow(display,event.xbutton.subwindow,
9168 event.xbutton.x,event.xbutton.y);
9169 if (target_window == (Window) NULL)
9170 target_window=root_window;
9171 x_offset=event.xbutton.x_root;
9172 y_offset=event.xbutton.y_root;
9173 crop_info->x=(ssize_t) x_offset;
9174 crop_info->y=(ssize_t) y_offset;
9176 crop_info->height=0;
9188 Discard pending button motion events.
9190 while (XCheckMaskEvent(display,ButtonMotionMask,&event)) ;
9191 crop_info->x=(ssize_t) event.xmotion.x;
9192 crop_info->y=(ssize_t) event.xmotion.y;
9194 Check boundary conditions.
9196 if ((int) crop_info->x < x_offset)
9197 crop_info->width=(size_t) (x_offset-crop_info->x);
9200 crop_info->width=(size_t) (crop_info->x-x_offset);
9201 crop_info->x=(ssize_t) x_offset;
9203 if ((int) crop_info->y < y_offset)
9204 crop_info->height=(size_t) (y_offset-crop_info->y);
9207 crop_info->height=(size_t) (crop_info->y-y_offset);
9208 crop_info->y=(ssize_t) y_offset;
9214 } while ((target_window == (Window) NULL) || (presses > 0));
9215 (void) XUngrabPointer(display,CurrentTime);
9216 (void) XFreeCursor(display,target_cursor);
9217 (void) XFreeGC(display,annotate_context);
9218 if ((crop_info->width*crop_info->height) < MinimumCropArea)
9221 crop_info->height=0;
9223 if ((crop_info->width != 0) && (crop_info->height != 0))
9224 target_window=root_window;
9225 return(target_window);
9229 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9233 % X S e t C u r s o r S t a t e %
9237 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9239 % XSetCursorState() sets the cursor state to busy, otherwise the cursor are
9240 % reset to their default.
9242 % The format of the XXSetCursorState method is:
9244 % XSetCursorState(display,windows,const MagickStatusType state)
9246 % A description of each parameter follows:
9248 % o display: Specifies a connection to an X server; returned from
9251 % o windows: Specifies a pointer to a XWindows structure.
9253 % o state: An unsigned integer greater than 0 sets the cursor state
9254 % to busy, otherwise the cursor are reset to their default.
9257 MagickPrivate void XSetCursorState(Display *display,XWindows *windows,
9258 const MagickStatusType state)
9260 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
9261 assert(display != (Display *) NULL);
9262 assert(windows != (XWindows *) NULL);
9265 (void) XCheckDefineCursor(display,windows->image.id,
9266 windows->image.busy_cursor);
9267 (void) XCheckDefineCursor(display,windows->pan.id,
9268 windows->pan.busy_cursor);
9269 (void) XCheckDefineCursor(display,windows->magnify.id,
9270 windows->magnify.busy_cursor);
9271 (void) XCheckDefineCursor(display,windows->command.id,
9272 windows->command.busy_cursor);
9276 (void) XCheckDefineCursor(display,windows->image.id,
9277 windows->image.cursor);
9278 (void) XCheckDefineCursor(display,windows->pan.id,windows->pan.cursor);
9279 (void) XCheckDefineCursor(display,windows->magnify.id,
9280 windows->magnify.cursor);
9281 (void) XCheckDefineCursor(display,windows->command.id,
9282 windows->command.cursor);
9283 (void) XCheckDefineCursor(display,windows->command.id,
9284 windows->widget.cursor);
9285 (void) XWithdrawWindow(display,windows->info.id,windows->info.screen);
9287 windows->info.mapped=MagickFalse;
9291 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9295 % X S e t W i n d o w s %
9299 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9301 % XSetWindows() sets the X windows structure if the windows info is specified.
9302 % Otherwise the current windows structure is returned.
9304 % The format of the XSetWindows method is:
9306 % XWindows *XSetWindows(XWindows *windows_info)
9308 % A description of each parameter follows:
9310 % o windows_info: Initialize the Windows structure with this information.
9313 MagickPrivate XWindows *XSetWindows(XWindows *windows_info)
9316 *windows = (XWindows *) NULL;
9318 if (windows_info != (XWindows *) ~0)
9320 windows=(XWindows *) RelinquishMagickMemory(windows);
9321 windows=windows_info;
9326 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9330 % X U s e r P r e f e r e n c e s %
9334 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9336 % XUserPreferences() saves the preferences in a configuration file in the
9337 % users' home directory.
9339 % The format of the XUserPreferences method is:
9341 % void XUserPreferences(XResourceInfo *resource_info)
9343 % A description of each parameter follows:
9345 % o resource_info: Specifies a pointer to a X11 XResourceInfo structure.
9348 MagickPrivate void XUserPreferences(XResourceInfo *resource_info)
9350 #if defined(X11_PREFERENCES_PATH)
9352 cache[MaxTextExtent],
9353 filename[MaxTextExtent],
9354 specifier[MaxTextExtent];
9361 preferences_database;
9364 Save user preferences to the client configuration file.
9366 assert(resource_info != (XResourceInfo *) NULL);
9367 client_name=GetClientName();
9368 preferences_database=XrmGetStringDatabase("");
9369 (void) FormatLocaleString(specifier,MaxTextExtent,"%s.backdrop",client_name);
9370 value=resource_info->backdrop ? "True" : "False";
9371 XrmPutStringResource(&preferences_database,specifier,(char *) value);
9372 (void) FormatLocaleString(specifier,MaxTextExtent,"%s.colormap",client_name);
9373 value=resource_info->colormap == SharedColormap ? "Shared" : "Private";
9374 XrmPutStringResource(&preferences_database,specifier,(char *) value);
9375 (void) FormatLocaleString(specifier,MaxTextExtent,"%s.confirmExit",
9377 value=resource_info->confirm_exit ? "True" : "False";
9378 XrmPutStringResource(&preferences_database,specifier,(char *) value);
9379 (void) FormatLocaleString(specifier,MaxTextExtent,"%s.confirmEdit",
9381 value=resource_info->confirm_edit ? "True" : "False";
9382 XrmPutStringResource(&preferences_database,specifier,(char *) value);
9383 (void) FormatLocaleString(specifier,MaxTextExtent,"%s.displayWarnings",
9385 value=resource_info->display_warnings ? "True" : "False";
9386 XrmPutStringResource(&preferences_database,specifier,(char *) value);
9387 (void) FormatLocaleString(specifier,MaxTextExtent,"%s.dither",client_name);
9388 value=resource_info->quantize_info->dither ? "True" : "False";
9389 XrmPutStringResource(&preferences_database,specifier,(char *) value);
9390 (void) FormatLocaleString(specifier,MaxTextExtent,"%s.gammaCorrect",
9392 value=resource_info->gamma_correct ? "True" : "False";
9393 XrmPutStringResource(&preferences_database,specifier,(char *) value);
9394 (void) FormatLocaleString(specifier,MaxTextExtent,"%s.undoCache",client_name);
9395 (void) FormatLocaleString(cache,MaxTextExtent,"%.20g",(double)
9396 resource_info->undo_cache);
9397 XrmPutStringResource(&preferences_database,specifier,cache);
9398 (void) FormatLocaleString(specifier,MaxTextExtent,"%s.usePixmap",client_name);
9399 value=resource_info->use_pixmap ? "True" : "False";
9400 XrmPutStringResource(&preferences_database,specifier,(char *) value);
9401 (void) FormatLocaleString(filename,MaxTextExtent,"%s%src",
9402 X11_PREFERENCES_PATH,client_name);
9403 ExpandFilename(filename);
9404 XrmPutFileDatabase(preferences_database,filename);
9409 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9413 % X V i s u a l C l a s s N a m e %
9417 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9419 % XVisualClassName() returns the visual class name as a character string.
9421 % The format of the XVisualClassName method is:
9423 % char *XVisualClassName(const int visual_class)
9425 % A description of each parameter follows:
9427 % o visual_type: XVisualClassName returns the visual class as a character
9430 % o class: Specifies the visual class.
9433 static const char *XVisualClassName(const int visual_class)
9435 switch (visual_class)
9437 case StaticGray: return("StaticGray");
9438 case GrayScale: return("GrayScale");
9439 case StaticColor: return("StaticColor");
9440 case PseudoColor: return("PseudoColor");
9441 case TrueColor: return("TrueColor");
9442 case DirectColor: return("DirectColor");
9444 return("unknown visual class");
9448 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9456 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9458 % XWarning() displays a warning reason in a Notice widget.
9460 % The format of the XWarning method is:
9462 % void XWarning(const unsigned int warning,const char *reason,
9463 % const char *description)
9465 % A description of each parameter follows:
9467 % o warning: Specifies the numeric warning category.
9469 % o reason: Specifies the reason to display before terminating the
9472 % o description: Specifies any description to the reason.
9475 MagickPrivate void XWarning(const ExceptionType magick_unused(warning),
9476 const char *reason,const char *description)
9479 text[MaxTextExtent];
9484 if (reason == (char *) NULL)
9486 (void) CopyMagickString(text,reason,MaxTextExtent);
9487 (void) ConcatenateMagickString(text,":",MaxTextExtent);
9488 windows=XSetWindows((XWindows *) ~0);
9489 XNoticeWidget(windows->display,windows,text,(char *) description);
9493 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9497 % X W i n d o w B y I D %
9501 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9503 % XWindowByID() locates a child window with a given ID. If not window with
9504 % the given name is found, 0 is returned. Only the window specified and its
9505 % subwindows are searched.
9507 % The format of the XWindowByID function is:
9509 % child=XWindowByID(display,window,id)
9511 % A description of each parameter follows:
9513 % o child: XWindowByID returns the window with the specified
9514 % id. If no windows are found, XWindowByID returns 0.
9516 % o display: Specifies a pointer to the Display structure; returned from
9519 % o id: Specifies the id of the window to locate.
9522 MagickPrivate Window XWindowByID(Display *display,const Window root_window,
9542 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
9543 assert(display != (Display *) NULL);
9544 assert(root_window != (Window) NULL);
9546 return(XSelectWindow(display,&rectangle_info));
9547 if (root_window == id)
9548 return(root_window);
9549 status=XQueryTree(display,root_window,&child,&child,&children,
9551 if (status == False)
9552 return((Window) NULL);
9553 window=(Window) NULL;
9554 for (i=0; i < (int) number_children; i++)
9557 Search each child and their children.
9559 window=XWindowByID(display,children[i],id);
9560 if (window != (Window) NULL)
9563 if (children != (Window *) NULL)
9564 (void) XFree((void *) children);
9569 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9573 % X W i n d o w B y N a m e %
9577 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9579 % XWindowByName() locates a window with a given name on a display. If no
9580 % window with the given name is found, 0 is returned. If more than one window
9581 % has the given name, the first one is returned. Only root and its children
9584 % The format of the XWindowByName function is:
9586 % window=XWindowByName(display,root_window,name)
9588 % A description of each parameter follows:
9590 % o window: XWindowByName returns the window id.
9592 % o display: Specifies a pointer to the Display structure; returned from
9595 % o root_window: Specifies the id of the root window.
9597 % o name: Specifies the name of the window to locate.
9600 MagickPrivate Window XWindowByName(Display *display,const Window root_window,
9620 assert(display != (Display *) NULL);
9621 assert(root_window != (Window) NULL);
9622 assert(name != (char *) NULL);
9623 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",name);
9624 if (XGetWMName(display,root_window,&window_name) != 0)
9625 if (LocaleCompare((char *) window_name.value,name) == 0)
9626 return(root_window);
9627 status=XQueryTree(display,root_window,&child,&child,&children,
9629 if (status == False)
9630 return((Window) NULL);
9631 window=(Window) NULL;
9632 for (i=0; i < (int) number_children; i++)
9635 Search each child and their children.
9637 window=XWindowByName(display,children[i],name);
9638 if (window != (Window) NULL)
9641 if (children != (Window *) NULL)
9642 (void) XFree((void *) children);
9647 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9651 % X W i n d o w B y P r o p e r y %
9655 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9657 % XWindowByProperty() locates a child window with a given property. If not
9658 % window with the given name is found, 0 is returned. If more than one window
9659 % has the given property, the first one is returned. Only the window
9660 % specified and its subwindows are searched.
9662 % The format of the XWindowByProperty function is:
9664 % child=XWindowByProperty(display,window,property)
9666 % A description of each parameter follows:
9668 % o child: XWindowByProperty returns the window id with the specified
9669 % property. If no windows are found, XWindowByProperty returns 0.
9671 % o display: Specifies a pointer to the Display structure; returned from
9674 % o property: Specifies the property of the window to locate.
9677 MagickPrivate Window XWindowByProperty(Display *display,const Window window,
9678 const Atom property)
9706 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
9707 assert(display != (Display *) NULL);
9708 assert(window != (Window) NULL);
9709 assert(property != (Atom) NULL);
9710 status=XQueryTree(display,window,&root,&parent,&children,&number_children);
9711 if (status == False)
9712 return((Window) NULL);
9714 child=(Window) NULL;
9715 for (i=0; (i < number_children) && (child == (Window) NULL); i++)
9717 status=XGetWindowProperty(display,children[i],property,0L,0L,MagickFalse,
9718 (Atom) AnyPropertyType,&type,&format,&number_items,&after,&data);
9720 (void) XFree((void *) data);
9721 if ((status == Success) && (type != (Atom) NULL))
9724 for (i=0; (i < number_children) && (child == (Window) NULL); i++)
9725 child=XWindowByProperty(display,children[i],property);
9726 if (children != (Window *) NULL)
9727 (void) XFree((void *) children);
9733 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9737 % X I m p o r t I m a g e %
9741 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9743 % XImportImage() reads an image from an X window.
9745 % The format of the XImportImage method is:
9747 % Image *XImportImage(const ImageInfo *image_info,XImportInfo *ximage_info,
9748 % ExceptionInfo *exception)
9750 % A description of each parameter follows:
9752 % o image_info: the image info..
9754 % o ximage_info: Specifies a pointer to an XImportInfo structure.
9756 % o exception: return any errors or warnings in this structure.
9759 MagickPrivate Image *XImportImage(const ImageInfo *image_info,
9760 XImportInfo *ximage_info,ExceptionInfo *exception)
9762 assert(image_info != (const ImageInfo *) NULL);
9763 assert(image_info->signature == MagickSignature);
9764 if (image_info->debug != MagickFalse)
9765 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
9766 image_info->filename);
9767 assert(ximage_info != (XImportInfo *) NULL);
9768 assert(exception != (ExceptionInfo *) NULL);
9769 assert(exception->signature == MagickSignature);
9770 return((Image *) NULL);
9775 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9779 + X C o m p o n e n t G e n e s i s %
9783 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9785 % XComponentGenesis() instantiates the X component.
9787 % The format of the XComponentGenesis method is:
9789 % MagickBooleanType XComponentGenesis(void)
9792 MagickPrivate MagickBooleanType XComponentGenesis(void)
9798 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9802 % X G e t I m p o r t I n f o %
9806 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
9808 % XGetImportInfo() initializes the XImportInfo structure.
9810 % The format of the XGetImportInfo method is:
9812 % void XGetImportInfo(XImportInfo *ximage_info)
9814 % A description of each parameter follows:
9816 % o ximage_info: Specifies a pointer to an ImageInfo structure.
9819 MagickExport void XGetImportInfo(XImportInfo *ximage_info)
9821 assert(ximage_info != (XImportInfo *) NULL);
9822 ximage_info->frame=MagickFalse;
9823 ximage_info->borders=MagickFalse;
9824 ximage_info->screen=MagickFalse;
9825 ximage_info->descend=MagickTrue;
9826 ximage_info->silent=MagickFalse;