aboutsummaryrefslogtreecommitdiffstats
path: root/src/image.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/image.c')
-rw-r--r--src/image.c564
1 files changed, 380 insertions, 184 deletions
diff --git a/src/image.c b/src/image.c
index f9f6ce70040..2c288342028 100644
--- a/src/image.c
+++ b/src/image.c
@@ -106,8 +106,6 @@ typedef struct ns_bitmap_record Bitmap_Record;
106#define GET_PIXEL(ximg, x, y) XGetPixel (ximg, x, y) 106#define GET_PIXEL(ximg, x, y) XGetPixel (ximg, x, y)
107#define NO_PIXMAP 0 107#define NO_PIXMAP 0
108 108
109#define ZPixmap 0
110
111#define PIX_MASK_RETAIN 0 109#define PIX_MASK_RETAIN 0
112#define PIX_MASK_DRAW 1 110#define PIX_MASK_DRAW 1
113 111
@@ -132,6 +130,8 @@ static void free_color_table (void);
132static unsigned long *colors_in_color_table (int *n); 130static unsigned long *colors_in_color_table (int *n);
133#endif 131#endif
134 132
133static Lisp_Object QCmax_width, QCmax_height;
134
135/* Code to deal with bitmaps. Bitmaps are referenced by their bitmap 135/* Code to deal with bitmaps. Bitmaps are referenced by their bitmap
136 id, which is just an int that this section returns. Bitmaps are 136 id, which is just an int that this section returns. Bitmaps are
137 reference counted so they can be shared among frames. 137 reference counted so they can be shared among frames.
@@ -144,16 +144,6 @@ static unsigned long *colors_in_color_table (int *n);
144 data more than once will not be caught. */ 144 data more than once will not be caught. */
145 145
146#ifdef HAVE_NS 146#ifdef HAVE_NS
147XImagePtr
148XGetImage (Display *display, Pixmap pixmap, int x, int y,
149 unsigned int width, unsigned int height,
150 unsigned long plane_mask, int format)
151{
152 /* TODO: not sure what this function is supposed to do.. */
153 ns_retain_object (pixmap);
154 return pixmap;
155}
156
157/* Use with images created by ns_image_for_XPM. */ 147/* Use with images created by ns_image_for_XPM. */
158unsigned long 148unsigned long
159XGetPixel (XImagePtr ximage, int x, int y) 149XGetPixel (XImagePtr ximage, int x, int y)
@@ -433,8 +423,24 @@ static bool x_create_x_image_and_pixmap (struct frame *, int, int, int,
433 XImagePtr *, Pixmap *); 423 XImagePtr *, Pixmap *);
434static void x_destroy_x_image (XImagePtr ximg); 424static void x_destroy_x_image (XImagePtr ximg);
435 425
426#ifdef HAVE_NTGUI
427static XImagePtr_or_DC image_get_x_image_or_dc (struct frame *, struct image *,
428 bool, HGDIOBJ *);
429static void image_unget_x_image_or_dc (struct image *, bool, XImagePtr_or_DC,
430 HGDIOBJ);
431#else
432static XImagePtr image_get_x_image (struct frame *, struct image *, bool);
433static void image_unget_x_image (struct image *, bool, XImagePtr);
434#define image_get_x_image_or_dc(f, img, mask_p, dummy) \
435 image_get_x_image (f, img, mask_p)
436#define image_unget_x_image_or_dc(img, mask_p, ximg, dummy) \
437 image_unget_x_image (img, mask_p, ximg)
438#endif
439
436#ifdef HAVE_X_WINDOWS 440#ifdef HAVE_X_WINDOWS
437 441
442static void image_sync_to_pixmaps (struct frame *, struct image *);
443
438/* Useful functions defined in the section 444/* Useful functions defined in the section
439 `Image type independent image structures' below. */ 445 `Image type independent image structures' below. */
440 446
@@ -1048,6 +1054,14 @@ prepare_image_for_display (struct frame *f, struct image *img)
1048 if (img->pixmap == NO_PIXMAP && !img->load_failed_p) 1054 if (img->pixmap == NO_PIXMAP && !img->load_failed_p)
1049 img->load_failed_p = ! img->type->load (f, img); 1055 img->load_failed_p = ! img->type->load (f, img);
1050 1056
1057#ifdef HAVE_X_WINDOWS
1058 if (!img->load_failed_p)
1059 {
1060 block_input ();
1061 image_sync_to_pixmaps (f, img);
1062 unblock_input ();
1063 }
1064#endif
1051} 1065}
1052 1066
1053 1067
@@ -1143,25 +1157,16 @@ four_corners_best (XImagePtr_or_DC ximg, int *corners,
1143 1157
1144#ifdef HAVE_NTGUI 1158#ifdef HAVE_NTGUI
1145 1159
1146#define Destroy_Image(img_dc, prev) \
1147 do { SelectObject (img_dc, prev); DeleteDC (img_dc); } while (0)
1148
1149#define Free_Pixmap(display, pixmap) \ 1160#define Free_Pixmap(display, pixmap) \
1150 DeleteObject (pixmap) 1161 DeleteObject (pixmap)
1151 1162
1152#elif defined (HAVE_NS) 1163#elif defined (HAVE_NS)
1153 1164
1154#define Destroy_Image(ximg, dummy) \
1155 ns_release_object (ximg)
1156
1157#define Free_Pixmap(display, pixmap) \ 1165#define Free_Pixmap(display, pixmap) \
1158 ns_release_object (pixmap) 1166 ns_release_object (pixmap)
1159 1167
1160#else 1168#else
1161 1169
1162#define Destroy_Image(ximg, dummy) \
1163 XDestroyImage (ximg)
1164
1165#define Free_Pixmap(display, pixmap) \ 1170#define Free_Pixmap(display, pixmap) \
1166 XFreePixmap (display, pixmap) 1171 XFreePixmap (display, pixmap)
1167 1172
@@ -1185,22 +1190,12 @@ image_background (struct image *img, struct frame *f, XImagePtr_or_DC ximg)
1185#endif /* HAVE_NTGUI */ 1190#endif /* HAVE_NTGUI */
1186 1191
1187 if (free_ximg) 1192 if (free_ximg)
1188 { 1193 ximg = image_get_x_image_or_dc (f, img, 0, &prev);
1189#ifndef HAVE_NTGUI
1190 ximg = XGetImage (FRAME_X_DISPLAY (f), img->pixmap,
1191 0, 0, img->width, img->height, ~0, ZPixmap);
1192#else
1193 HDC frame_dc = get_frame_dc (f);
1194 ximg = CreateCompatibleDC (frame_dc);
1195 release_frame_dc (f, frame_dc);
1196 prev = SelectObject (ximg, img->pixmap);
1197#endif /* !HAVE_NTGUI */
1198 }
1199 1194
1200 img->background = four_corners_best (ximg, img->corners, img->width, img->height); 1195 img->background = four_corners_best (ximg, img->corners, img->width, img->height);
1201 1196
1202 if (free_ximg) 1197 if (free_ximg)
1203 Destroy_Image (ximg, prev); 1198 image_unget_x_image_or_dc (img, 0, ximg, prev);
1204 1199
1205 img->background_valid = 1; 1200 img->background_valid = 1;
1206 } 1201 }
@@ -1226,23 +1221,13 @@ image_background_transparent (struct image *img, struct frame *f, XImagePtr_or_D
1226#endif /* HAVE_NTGUI */ 1221#endif /* HAVE_NTGUI */
1227 1222
1228 if (free_mask) 1223 if (free_mask)
1229 { 1224 mask = image_get_x_image_or_dc (f, img, 1, &prev);
1230#ifndef HAVE_NTGUI
1231 mask = XGetImage (FRAME_X_DISPLAY (f), img->mask,
1232 0, 0, img->width, img->height, ~0, ZPixmap);
1233#else
1234 HDC frame_dc = get_frame_dc (f);
1235 mask = CreateCompatibleDC (frame_dc);
1236 release_frame_dc (f, frame_dc);
1237 prev = SelectObject (mask, img->mask);
1238#endif /* HAVE_NTGUI */
1239 }
1240 1225
1241 img->background_transparent 1226 img->background_transparent
1242 = (four_corners_best (mask, img->corners, img->width, img->height) == PIX_MASK_RETAIN); 1227 = (four_corners_best (mask, img->corners, img->width, img->height) == PIX_MASK_RETAIN);
1243 1228
1244 if (free_mask) 1229 if (free_mask)
1245 Destroy_Image (mask, prev); 1230 image_unget_x_image_or_dc (img, 1, mask, prev);
1246 } 1231 }
1247 else 1232 else
1248 img->background_transparent = 0; 1233 img->background_transparent = 0;
@@ -1258,30 +1243,58 @@ image_background_transparent (struct image *img, struct frame *f, XImagePtr_or_D
1258 Helper functions for X image types 1243 Helper functions for X image types
1259 ***********************************************************************/ 1244 ***********************************************************************/
1260 1245
1261/* Clear X resources of image IMG on frame F. PIXMAP_P means free the 1246/* Clear X resources of image IMG on frame F according to FLAGS.
1262 pixmap if any. MASK_P means clear the mask pixmap if any. 1247 FLAGS is bitwise-or of the following masks:
1263 COLORS_P means free colors allocated for the image, if any. */ 1248 CLEAR_IMAGE_PIXMAP free the pixmap if any.
1249 CLEAR_IMAGE_MASK means clear the mask pixmap if any.
1250 CLEAR_IMAGE_COLORS means free colors allocated for the image, if
1251 any. */
1252
1253#define CLEAR_IMAGE_PIXMAP (1 << 0)
1254#define CLEAR_IMAGE_MASK (1 << 1)
1255#define CLEAR_IMAGE_COLORS (1 << 2)
1264 1256
1265static void 1257static void
1266x_clear_image_1 (struct frame *f, struct image *img, bool pixmap_p, 1258x_clear_image_1 (struct frame *f, struct image *img, int flags)
1267 bool mask_p, bool colors_p)
1268{ 1259{
1269 if (pixmap_p && img->pixmap) 1260 if (flags & CLEAR_IMAGE_PIXMAP)
1270 { 1261 {
1271 Free_Pixmap (FRAME_X_DISPLAY (f), img->pixmap); 1262 if (img->pixmap)
1272 img->pixmap = NO_PIXMAP; 1263 {
1273 /* NOTE (HAVE_NS): background color is NOT an indexed color! */ 1264 Free_Pixmap (FRAME_X_DISPLAY (f), img->pixmap);
1274 img->background_valid = 0; 1265 img->pixmap = NO_PIXMAP;
1266 /* NOTE (HAVE_NS): background color is NOT an indexed color! */
1267 img->background_valid = 0;
1268 }
1269#ifdef HAVE_X_WINDOWS
1270 if (img->ximg)
1271 {
1272 x_destroy_x_image (img->ximg);
1273 img->ximg = NULL;
1274 img->background_valid = 0;
1275 }
1276#endif
1275 } 1277 }
1276 1278
1277 if (mask_p && img->mask) 1279 if (flags & CLEAR_IMAGE_MASK)
1278 { 1280 {
1279 Free_Pixmap (FRAME_X_DISPLAY (f), img->mask); 1281 if (img->mask)
1280 img->mask = NO_PIXMAP; 1282 {
1281 img->background_transparent_valid = 0; 1283 Free_Pixmap (FRAME_X_DISPLAY (f), img->mask);
1284 img->mask = NO_PIXMAP;
1285 img->background_transparent_valid = 0;
1286 }
1287#ifdef HAVE_X_WINDOWS
1288 if (img->mask_img)
1289 {
1290 x_destroy_x_image (img->mask_img);
1291 img->mask_img = NULL;
1292 img->background_transparent_valid = 0;
1293 }
1294#endif
1282 } 1295 }
1283 1296
1284 if (colors_p && img->ncolors) 1297 if ((flags & CLEAR_IMAGE_COLORS) && img->ncolors)
1285 { 1298 {
1286 /* W32_TODO: color table support. */ 1299 /* W32_TODO: color table support. */
1287#ifdef HAVE_X_WINDOWS 1300#ifdef HAVE_X_WINDOWS
@@ -1300,7 +1313,8 @@ static void
1300x_clear_image (struct frame *f, struct image *img) 1313x_clear_image (struct frame *f, struct image *img)
1301{ 1314{
1302 block_input (); 1315 block_input ();
1303 x_clear_image_1 (f, img, 1, 1, 1); 1316 x_clear_image_1 (f, img,
1317 CLEAR_IMAGE_PIXMAP | CLEAR_IMAGE_MASK | CLEAR_IMAGE_COLORS);
1304 unblock_input (); 1318 unblock_input ();
1305} 1319}
1306 1320
@@ -1631,10 +1645,7 @@ postprocess_image (struct frame *f, struct image *img)
1631 x_build_heuristic_mask (f, img, XCDR (mask)); 1645 x_build_heuristic_mask (f, img, XCDR (mask));
1632 } 1646 }
1633 else if (NILP (mask) && found_p && img->mask) 1647 else if (NILP (mask) && found_p && img->mask)
1634 { 1648 x_clear_image_1 (f, img, CLEAR_IMAGE_MASK);
1635 Free_Pixmap (FRAME_X_DISPLAY (f), img->mask);
1636 img->mask = NO_PIXMAP;
1637 }
1638 } 1649 }
1639 1650
1640 1651
@@ -2092,6 +2103,134 @@ x_put_x_image (struct frame *f, XImagePtr ximg, Pixmap pixmap, int width, int he
2092#endif 2103#endif
2093} 2104}
2094 2105
2106/* Thin wrapper for x_create_x_image_and_pixmap, so that it matches
2107 with image_put_x_image. */
2108
2109static bool
2110image_create_x_image_and_pixmap (struct frame *f, struct image *img,
2111 int width, int height, int depth,
2112 XImagePtr *ximg, bool mask_p)
2113{
2114 eassert ((!mask_p ? img->pixmap : img->mask) == NO_PIXMAP);
2115
2116 return x_create_x_image_and_pixmap (f, width, height, depth, ximg,
2117 !mask_p ? &img->pixmap : &img->mask);
2118}
2119
2120/* Put X image XIMG into image IMG on frame F, as a mask if and only
2121 if MASK_P. On X, this simply records XIMG on a member of IMG, so
2122 it can be put into the pixmap afterwards via image_sync_to_pixmaps.
2123 On the other platforms, it puts XIMG into the pixmap, then frees
2124 the X image and its buffer. */
2125
2126static void
2127image_put_x_image (struct frame *f, struct image *img, XImagePtr ximg,
2128 bool mask_p)
2129{
2130#ifdef HAVE_X_WINDOWS
2131 if (!mask_p)
2132 {
2133 eassert (img->ximg == NULL);
2134 img->ximg = ximg;
2135 }
2136 else
2137 {
2138 eassert (img->mask_img == NULL);
2139 img->mask_img = ximg;
2140 }
2141#else
2142 x_put_x_image (f, ximg, !mask_p ? img->pixmap : img->mask,
2143 img->width, img->height);
2144 x_destroy_x_image (ximg);
2145#endif
2146}
2147
2148#ifdef HAVE_X_WINDOWS
2149/* Put the X images recorded in IMG on frame F into pixmaps, then free
2150 the X images and their buffers. */
2151
2152static void
2153image_sync_to_pixmaps (struct frame *f, struct image *img)
2154{
2155 if (img->ximg)
2156 {
2157 x_put_x_image (f, img->ximg, img->pixmap, img->width, img->height);
2158 x_destroy_x_image (img->ximg);
2159 img->ximg = NULL;
2160 }
2161 if (img->mask_img)
2162 {
2163 x_put_x_image (f, img->mask_img, img->mask, img->width, img->height);
2164 x_destroy_x_image (img->mask_img);
2165 img->mask_img = NULL;
2166 }
2167}
2168#endif
2169
2170#ifdef HAVE_NTGUI
2171/* Create a memory device context for IMG on frame F. It stores the
2172 currently selected GDI object into *PREV for future restoration by
2173 image_unget_x_image_or_dc. */
2174
2175static XImagePtr_or_DC
2176image_get_x_image_or_dc (struct frame *f, struct image *img, bool mask_p,
2177 HGDIOBJ *prev)
2178{
2179 HDC frame_dc = get_frame_dc (f);
2180 XImagePtr_or_DC ximg = CreateCompatibleDC (frame_dc);
2181
2182 release_frame_dc (f, frame_dc);
2183 *prev = SelectObject (ximg, !mask_p ? img->pixmap : img->mask);
2184
2185 return ximg;
2186}
2187
2188static void
2189image_unget_x_image_or_dc (struct image *img, bool mask_p,
2190 XImagePtr_or_DC ximg, HGDIOBJ prev)
2191{
2192 SelectObject (ximg, prev);
2193 DeleteDC (ximg);
2194}
2195#else /* !HAVE_NTGUI */
2196/* Get the X image for IMG on frame F. The resulting X image data
2197 should be treated as read-only at least on X. */
2198
2199static XImagePtr
2200image_get_x_image (struct frame *f, struct image *img, bool mask_p)
2201{
2202#ifdef HAVE_X_WINDOWS
2203 XImagePtr ximg_in_img = !mask_p ? img->ximg : img->mask_img;
2204
2205 if (ximg_in_img)
2206 return ximg_in_img;
2207 else
2208 return XGetImage (FRAME_X_DISPLAY (f), !mask_p ? img->pixmap : img->mask,
2209 0, 0, img->width, img->height, ~0, ZPixmap);
2210#elif defined (HAVE_NS)
2211 XImagePtr pixmap = !mask_p ? img->pixmap : img->mask;
2212
2213 ns_retain_object (pixmap);
2214 return pixmap;
2215#endif
2216}
2217
2218static void
2219image_unget_x_image (struct image *img, bool mask_p, XImagePtr ximg)
2220{
2221#ifdef HAVE_X_WINDOWS
2222 XImagePtr ximg_in_img = !mask_p ? img->ximg : img->mask_img;
2223
2224 if (ximg_in_img)
2225 eassert (ximg == ximg_in_img);
2226 else
2227 XDestroyImage (ximg);
2228#elif defined (HAVE_NS)
2229 ns_release_object (ximg);
2230#endif
2231}
2232#endif /* !HAVE_NTGUI */
2233
2095 2234
2096/*********************************************************************** 2235/***********************************************************************
2097 File Handling 2236 File Handling
@@ -3057,7 +3196,7 @@ struct xpm_cached_color
3057 XColor color; 3196 XColor color;
3058 3197
3059 /* Color name. */ 3198 /* Color name. */
3060 char name[1]; 3199 char name[FLEXIBLE_ARRAY_MEMBER];
3061}; 3200};
3062 3201
3063/* The hash table used for the color cache, and its bucket vector 3202/* The hash table used for the color cache, and its bucket vector
@@ -3459,9 +3598,9 @@ xpm_load (struct frame *f, struct image *img)
3459 &xpm_image, &xpm_mask, 3598 &xpm_image, &xpm_mask,
3460 &attrs); 3599 &attrs);
3461#else 3600#else
3462 rc = XpmReadFileToPixmap (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), 3601 rc = XpmReadFileToImage (FRAME_X_DISPLAY (f), SSDATA (file),
3463 SSDATA (file), &img->pixmap, &img->mask, 3602 &img->ximg, &img->mask_img,
3464 &attrs); 3603 &attrs);
3465#endif /* HAVE_NTGUI */ 3604#endif /* HAVE_NTGUI */
3466 } 3605 }
3467 else 3606 else
@@ -3482,13 +3621,38 @@ xpm_load (struct frame *f, struct image *img)
3482 &xpm_image, &xpm_mask, 3621 &xpm_image, &xpm_mask,
3483 &attrs); 3622 &attrs);
3484#else 3623#else
3485 rc = XpmCreatePixmapFromBuffer (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), 3624 rc = XpmCreateImageFromBuffer (FRAME_X_DISPLAY (f), SSDATA (buffer),
3486 SSDATA (buffer), 3625 &img->ximg, &img->mask_img,
3487 &img->pixmap, &img->mask, 3626 &attrs);
3488 &attrs);
3489#endif /* HAVE_NTGUI */ 3627#endif /* HAVE_NTGUI */
3490 } 3628 }
3491 3629
3630#ifdef HAVE_X_WINDOWS
3631 if (rc == XpmSuccess)
3632 {
3633 img->pixmap = XCreatePixmap (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
3634 img->ximg->width, img->ximg->height,
3635 img->ximg->depth);
3636 if (img->pixmap == NO_PIXMAP)
3637 {
3638 x_clear_image (f, img);
3639 rc = XpmNoMemory;
3640 }
3641 else if (img->mask_img)
3642 {
3643 img->mask = XCreatePixmap (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f),
3644 img->mask_img->width,
3645 img->mask_img->height,
3646 img->mask_img->depth);
3647 if (img->mask == NO_PIXMAP)
3648 {
3649 x_clear_image (f, img);
3650 rc = XpmNoMemory;
3651 }
3652 }
3653 }
3654#endif
3655
3492 if (rc == XpmSuccess) 3656 if (rc == XpmSuccess)
3493 { 3657 {
3494#if defined (COLOR_TABLE_SUPPORT) && defined (ALLOC_XPM_COLORS) 3658#if defined (COLOR_TABLE_SUPPORT) && defined (ALLOC_XPM_COLORS)
@@ -3547,6 +3711,15 @@ xpm_load (struct frame *f, struct image *img)
3547#else 3711#else
3548 XpmFreeAttributes (&attrs); 3712 XpmFreeAttributes (&attrs);
3549#endif /* HAVE_NTGUI */ 3713#endif /* HAVE_NTGUI */
3714
3715#ifdef HAVE_X_WINDOWS
3716 /* Maybe fill in the background field while we have ximg handy. */
3717 IMAGE_BACKGROUND (img, f, img->ximg);
3718 if (img->mask_img)
3719 /* Fill in the background_transparent field while we have the
3720 mask handy. */
3721 image_background_transparent (img, f, img->mask_img);
3722#endif
3550 } 3723 }
3551 else 3724 else
3552 { 3725 {
@@ -3845,11 +4018,10 @@ xpm_load_image (struct frame *f,
3845 goto failure; 4018 goto failure;
3846 } 4019 }
3847 4020
3848 if (!x_create_x_image_and_pixmap (f, width, height, 0, 4021 if (!image_create_x_image_and_pixmap (f, img, width, height, 0, &ximg, 0)
3849 &ximg, &img->pixmap)
3850#ifndef HAVE_NS 4022#ifndef HAVE_NS
3851 || !x_create_x_image_and_pixmap (f, width, height, 1, 4023 || !image_create_x_image_and_pixmap (f, img, width, height, 1,
3852 &mask_img, &img->mask) 4024 &mask_img, 1)
3853#endif 4025#endif
3854 ) 4026 )
3855 { 4027 {
@@ -3984,8 +4156,7 @@ xpm_load_image (struct frame *f,
3984 if (NILP (image_spec_value (img->spec, QCbackground, NULL))) 4156 if (NILP (image_spec_value (img->spec, QCbackground, NULL)))
3985 IMAGE_BACKGROUND (img, f, ximg); 4157 IMAGE_BACKGROUND (img, f, ximg);
3986 4158
3987 x_put_x_image (f, ximg, img->pixmap, width, height); 4159 image_put_x_image (f, img, ximg, 0);
3988 x_destroy_x_image (ximg);
3989#ifndef HAVE_NS 4160#ifndef HAVE_NS
3990 if (have_mask) 4161 if (have_mask)
3991 { 4162 {
@@ -3993,14 +4164,12 @@ xpm_load_image (struct frame *f,
3993 mask handy. */ 4164 mask handy. */
3994 image_background_transparent (img, f, mask_img); 4165 image_background_transparent (img, f, mask_img);
3995 4166
3996 x_put_x_image (f, mask_img, img->mask, width, height); 4167 image_put_x_image (f, img, mask_img, 1);
3997 x_destroy_x_image (mask_img);
3998 } 4168 }
3999 else 4169 else
4000 { 4170 {
4001 x_destroy_x_image (mask_img); 4171 x_destroy_x_image (mask_img);
4002 Free_Pixmap (FRAME_X_DISPLAY (f), img->mask); 4172 x_clear_image_1 (f, img, CLEAR_IMAGE_MASK);
4003 img->mask = NO_PIXMAP;
4004 } 4173 }
4005#endif 4174#endif
4006 return 1; 4175 return 1;
@@ -4398,17 +4567,8 @@ x_to_xcolors (struct frame *f, struct image *img, bool rgb_p)
4398 memory_full (SIZE_MAX); 4567 memory_full (SIZE_MAX);
4399 colors = xmalloc (sizeof *colors * img->width * img->height); 4568 colors = xmalloc (sizeof *colors * img->width * img->height);
4400 4569
4401#ifndef HAVE_NTGUI 4570 /* Get the X image or create a memory device context for IMG. */
4402 /* Get the X image IMG->pixmap. */ 4571 ximg = image_get_x_image_or_dc (f, img, 0, &prev);
4403 ximg = XGetImage (FRAME_X_DISPLAY (f), img->pixmap,
4404 0, 0, img->width, img->height, ~0, ZPixmap);
4405#else
4406 /* Load the image into a memory device context. */
4407 hdc = get_frame_dc (f);
4408 ximg = CreateCompatibleDC (hdc);
4409 release_frame_dc (f, hdc);
4410 prev = SelectObject (ximg, img->pixmap);
4411#endif /* HAVE_NTGUI */
4412 4572
4413 /* Fill the `pixel' members of the XColor array. I wished there 4573 /* Fill the `pixel' members of the XColor array. I wished there
4414 were an easy and portable way to circumvent XGetPixel. */ 4574 were an easy and portable way to circumvent XGetPixel. */
@@ -4438,7 +4598,7 @@ x_to_xcolors (struct frame *f, struct image *img, bool rgb_p)
4438#endif /* HAVE_X_WINDOWS */ 4598#endif /* HAVE_X_WINDOWS */
4439 } 4599 }
4440 4600
4441 Destroy_Image (ximg, prev); 4601 image_unget_x_image_or_dc (img, 0, ximg, prev);
4442 4602
4443 return colors; 4603 return colors;
4444} 4604}
@@ -4498,13 +4658,13 @@ x_from_xcolors (struct frame *f, struct image *img, XColor *colors)
4498{ 4658{
4499 int x, y; 4659 int x, y;
4500 XImagePtr oimg = NULL; 4660 XImagePtr oimg = NULL;
4501 Pixmap pixmap;
4502 XColor *p; 4661 XColor *p;
4503 4662
4504 init_color_table (); 4663 init_color_table ();
4505 4664
4506 x_create_x_image_and_pixmap (f, img->width, img->height, 0, 4665 x_clear_image_1 (f, img, CLEAR_IMAGE_PIXMAP | CLEAR_IMAGE_COLORS);
4507 &oimg, &pixmap); 4666 image_create_x_image_and_pixmap (f, img, img->width, img->height, 0,
4667 &oimg, 0);
4508 p = colors; 4668 p = colors;
4509 for (y = 0; y < img->height; ++y) 4669 for (y = 0; y < img->height; ++y)
4510 for (x = 0; x < img->width; ++x, ++p) 4670 for (x = 0; x < img->width; ++x, ++p)
@@ -4515,11 +4675,8 @@ x_from_xcolors (struct frame *f, struct image *img, XColor *colors)
4515 } 4675 }
4516 4676
4517 xfree (colors); 4677 xfree (colors);
4518 x_clear_image_1 (f, img, 1, 0, 1);
4519 4678
4520 x_put_x_image (f, oimg, pixmap, img->width, img->height); 4679 image_put_x_image (f, img, oimg, 0);
4521 x_destroy_x_image (oimg);
4522 img->pixmap = pixmap;
4523#ifdef COLOR_TABLE_SUPPORT 4680#ifdef COLOR_TABLE_SUPPORT
4524 img->colors = colors_in_color_table (&img->ncolors); 4681 img->colors = colors_in_color_table (&img->ncolors);
4525 free_color_table (); 4682 free_color_table ();
@@ -4704,7 +4861,10 @@ x_disable_image (struct frame *f, struct image *img)
4704#define MaskForeground(f) WHITE_PIX_DEFAULT (f) 4861#define MaskForeground(f) WHITE_PIX_DEFAULT (f)
4705 4862
4706 Display *dpy = FRAME_X_DISPLAY (f); 4863 Display *dpy = FRAME_X_DISPLAY (f);
4707 GC gc = XCreateGC (dpy, img->pixmap, 0, NULL); 4864 GC gc;
4865
4866 image_sync_to_pixmaps (f, img);
4867 gc = XCreateGC (dpy, img->pixmap, 0, NULL);
4708 XSetForeground (dpy, gc, BLACK_PIX_DEFAULT (f)); 4868 XSetForeground (dpy, gc, BLACK_PIX_DEFAULT (f));
4709 XDrawLine (dpy, img->pixmap, gc, 0, 0, 4869 XDrawLine (dpy, img->pixmap, gc, 0, 0,
4710 img->width - 1, img->height - 1); 4870 img->width - 1, img->height - 1);
@@ -4779,37 +4939,25 @@ x_build_heuristic_mask (struct frame *f, struct image *img, Lisp_Object how)
4779 unsigned long bg = 0; 4939 unsigned long bg = 0;
4780 4940
4781 if (img->mask) 4941 if (img->mask)
4782 { 4942 x_clear_image_1 (f, img, CLEAR_IMAGE_MASK);
4783 Free_Pixmap (FRAME_X_DISPLAY (f), img->mask);
4784 img->mask = NO_PIXMAP;
4785 img->background_transparent_valid = 0;
4786 }
4787 4943
4788#ifndef HAVE_NTGUI 4944#ifndef HAVE_NTGUI
4789#ifndef HAVE_NS 4945#ifndef HAVE_NS
4790 /* Create an image and pixmap serving as mask. */ 4946 /* Create an image and pixmap serving as mask. */
4791 rc = x_create_x_image_and_pixmap (f, img->width, img->height, 1, 4947 rc = image_create_x_image_and_pixmap (f, img, img->width, img->height, 1,
4792 &mask_img, &img->mask); 4948 &mask_img, 1);
4793 if (!rc) 4949 if (!rc)
4794 return; 4950 return;
4795#endif /* !HAVE_NS */ 4951#endif /* !HAVE_NS */
4796
4797 /* Get the X image of IMG->pixmap. */
4798 ximg = XGetImage (FRAME_X_DISPLAY (f), img->pixmap, 0, 0,
4799 img->width, img->height,
4800 ~0, ZPixmap);
4801#else 4952#else
4802 /* Create the bit array serving as mask. */ 4953 /* Create the bit array serving as mask. */
4803 row_width = (img->width + 7) / 8; 4954 row_width = (img->width + 7) / 8;
4804 mask_img = xzalloc (row_width * img->height); 4955 mask_img = xzalloc (row_width * img->height);
4805
4806 /* Create a memory device context for IMG->pixmap. */
4807 frame_dc = get_frame_dc (f);
4808 ximg = CreateCompatibleDC (frame_dc);
4809 release_frame_dc (f, frame_dc);
4810 prev = SelectObject (ximg, img->pixmap);
4811#endif /* HAVE_NTGUI */ 4956#endif /* HAVE_NTGUI */
4812 4957
4958 /* Get the X image or create a memory device context for IMG. */
4959 ximg = image_get_x_image_or_dc (f, img, 0, &prev);
4960
4813 /* Determine the background color of ximg. If HOW is `(R G B)' 4961 /* Determine the background color of ximg. If HOW is `(R G B)'
4814 take that as color. Otherwise, use the image's background color. */ 4962 take that as color. Otherwise, use the image's background color. */
4815 use_img_background = 1; 4963 use_img_background = 1;
@@ -4856,9 +5004,8 @@ x_build_heuristic_mask (struct frame *f, struct image *img, Lisp_Object how)
4856 /* Fill in the background_transparent field while we have the mask handy. */ 5004 /* Fill in the background_transparent field while we have the mask handy. */
4857 image_background_transparent (img, f, mask_img); 5005 image_background_transparent (img, f, mask_img);
4858 5006
4859 /* Put mask_img into img->mask. */ 5007 /* Put mask_img into the image. */
4860 x_put_x_image (f, mask_img, img->mask, img->width, img->height); 5008 image_put_x_image (f, img, mask_img, 1);
4861 x_destroy_x_image (mask_img);
4862#endif /* !HAVE_NS */ 5009#endif /* !HAVE_NS */
4863#else 5010#else
4864 for (y = 0; y < img->height; ++y) 5011 for (y = 0; y < img->height; ++y)
@@ -4880,7 +5027,7 @@ x_build_heuristic_mask (struct frame *f, struct image *img, Lisp_Object how)
4880 xfree (mask_img); 5027 xfree (mask_img);
4881#endif /* HAVE_NTGUI */ 5028#endif /* HAVE_NTGUI */
4882 5029
4883 Destroy_Image (ximg, prev); 5030 image_unget_x_image_or_dc (img, 0, ximg, prev);
4884} 5031}
4885 5032
4886 5033
@@ -5108,8 +5255,7 @@ pbm_load (struct frame *f, struct image *img)
5108 goto error; 5255 goto error;
5109 } 5256 }
5110 5257
5111 if (!x_create_x_image_and_pixmap (f, width, height, 0, 5258 if (!image_create_x_image_and_pixmap (f, img, width, height, 0, &ximg, 0))
5112 &ximg, &img->pixmap))
5113 goto error; 5259 goto error;
5114 5260
5115 /* Initialize the color hash table. */ 5261 /* Initialize the color hash table. */
@@ -5246,9 +5392,8 @@ pbm_load (struct frame *f, struct image *img)
5246 /* Casting avoids a GCC warning. */ 5392 /* Casting avoids a GCC warning. */
5247 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg); 5393 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg);
5248 5394
5249 /* Put the image into a pixmap. */ 5395 /* Put ximg into the image. */
5250 x_put_x_image (f, ximg, img->pixmap, width, height); 5396 image_put_x_image (f, img, ximg, 0);
5251 x_destroy_x_image (ximg);
5252 5397
5253 /* X and W32 versions did it here, MAC version above. ++kfs 5398 /* X and W32 versions did it here, MAC version above. ++kfs
5254 img->width = width; 5399 img->width = width;
@@ -5686,8 +5831,7 @@ png_load_body (struct frame *f, struct image *img, struct png_load_context *c)
5686 5831
5687 /* Create the X image and pixmap now, so that the work below can be 5832 /* Create the X image and pixmap now, so that the work below can be
5688 omitted if the image is too large for X. */ 5833 omitted if the image is too large for X. */
5689 if (!x_create_x_image_and_pixmap (f, width, height, 0, &ximg, 5834 if (!image_create_x_image_and_pixmap (f, img, width, height, 0, &ximg, 0))
5690 &img->pixmap))
5691 goto error; 5835 goto error;
5692 5836
5693 /* If image contains simply transparency data, we prefer to 5837 /* If image contains simply transparency data, we prefer to
@@ -5799,12 +5943,11 @@ png_load_body (struct frame *f, struct image *img, struct png_load_context *c)
5799 contains an alpha channel. */ 5943 contains an alpha channel. */
5800 if (channels == 4 5944 if (channels == 4
5801 && !transparent_p 5945 && !transparent_p
5802 && !x_create_x_image_and_pixmap (f, width, height, 1, 5946 && !image_create_x_image_and_pixmap (f, img, width, height, 1,
5803 &mask_img, &img->mask)) 5947 &mask_img, 1))
5804 { 5948 {
5805 x_destroy_x_image (ximg); 5949 x_destroy_x_image (ximg);
5806 Free_Pixmap (FRAME_X_DISPLAY (f), img->pixmap); 5950 x_clear_image_1 (f, img, CLEAR_IMAGE_PIXMAP);
5807 img->pixmap = NO_PIXMAP;
5808 goto error; 5951 goto error;
5809 } 5952 }
5810 5953
@@ -5878,9 +6021,8 @@ png_load_body (struct frame *f, struct image *img, struct png_load_context *c)
5878 Casting avoids a GCC warning. */ 6021 Casting avoids a GCC warning. */
5879 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg); 6022 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg);
5880 6023
5881 /* Put the image into the pixmap, then free the X image and its buffer. */ 6024 /* Put ximg into the image. */
5882 x_put_x_image (f, ximg, img->pixmap, width, height); 6025 image_put_x_image (f, img, ximg, 0);
5883 x_destroy_x_image (ximg);
5884 6026
5885 /* Same for the mask. */ 6027 /* Same for the mask. */
5886 if (mask_img) 6028 if (mask_img)
@@ -5889,8 +6031,7 @@ png_load_body (struct frame *f, struct image *img, struct png_load_context *c)
5889 mask handy. Casting avoids a GCC warning. */ 6031 mask handy. Casting avoids a GCC warning. */
5890 image_background_transparent (img, f, (XImagePtr_or_DC)mask_img); 6032 image_background_transparent (img, f, (XImagePtr_or_DC)mask_img);
5891 6033
5892 x_put_x_image (f, mask_img, img->mask, img->width, img->height); 6034 image_put_x_image (f, img, mask_img, 1);
5893 x_destroy_x_image (mask_img);
5894 } 6035 }
5895 6036
5896 return 1; 6037 return 1;
@@ -6427,7 +6568,7 @@ jpeg_load_body (struct frame *f, struct image *img,
6427 } 6568 }
6428 6569
6429 /* Create X image and pixmap. */ 6570 /* Create X image and pixmap. */
6430 if (!x_create_x_image_and_pixmap (f, width, height, 0, &ximg, &img->pixmap)) 6571 if (!image_create_x_image_and_pixmap (f, img, width, height, 0, &ximg, 0))
6431 { 6572 {
6432 mgr->failure_code = MY_JPEG_CANNOT_CREATE_X; 6573 mgr->failure_code = MY_JPEG_CANNOT_CREATE_X;
6433 sys_longjmp (mgr->setjmp_buffer, 1); 6574 sys_longjmp (mgr->setjmp_buffer, 1);
@@ -6494,9 +6635,8 @@ jpeg_load_body (struct frame *f, struct image *img,
6494 /* Casting avoids a GCC warning. */ 6635 /* Casting avoids a GCC warning. */
6495 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg); 6636 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg);
6496 6637
6497 /* Put the image into the pixmap. */ 6638 /* Put ximg into the image. */
6498 x_put_x_image (f, ximg, img->pixmap, width, height); 6639 image_put_x_image (f, img, ximg, 0);
6499 x_destroy_x_image (ximg);
6500 return 1; 6640 return 1;
6501} 6641}
6502 6642
@@ -6893,8 +7033,8 @@ tiff_load (struct frame *f, struct image *img)
6893 7033
6894 /* Create the X image and pixmap. */ 7034 /* Create the X image and pixmap. */
6895 if (! (height <= min (PTRDIFF_MAX, SIZE_MAX) / sizeof *buf / width 7035 if (! (height <= min (PTRDIFF_MAX, SIZE_MAX) / sizeof *buf / width
6896 && x_create_x_image_and_pixmap (f, width, height, 0, 7036 && image_create_x_image_and_pixmap (f, img, width, height, 0,
6897 &ximg, &img->pixmap))) 7037 &ximg, 0)))
6898 { 7038 {
6899 fn_TIFFClose (tiff); 7039 fn_TIFFClose (tiff);
6900 return 0; 7040 return 0;
@@ -6953,9 +7093,8 @@ tiff_load (struct frame *f, struct image *img)
6953 /* Casting avoids a GCC warning on W32. */ 7093 /* Casting avoids a GCC warning on W32. */
6954 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg); 7094 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg);
6955 7095
6956 /* Put the image into the pixmap, then free the X image and its buffer. */ 7096 /* Put ximg into the image. */
6957 x_put_x_image (f, ximg, img->pixmap, width, height); 7097 image_put_x_image (f, img, ximg, 0);
6958 x_destroy_x_image (ximg);
6959 xfree (buf); 7098 xfree (buf);
6960 7099
6961 return 1; 7100 return 1;
@@ -7283,7 +7422,7 @@ gif_load (struct frame *f, struct image *img)
7283 } 7422 }
7284 7423
7285 /* Create the X image and pixmap. */ 7424 /* Create the X image and pixmap. */
7286 if (!x_create_x_image_and_pixmap (f, width, height, 0, &ximg, &img->pixmap)) 7425 if (!image_create_x_image_and_pixmap (f, img, width, height, 0, &ximg, 0))
7287 { 7426 {
7288 fn_DGifCloseFile (gif); 7427 fn_DGifCloseFile (gif);
7289 return 0; 7428 return 0;
@@ -7467,9 +7606,8 @@ gif_load (struct frame *f, struct image *img)
7467 /* Casting avoids a GCC warning. */ 7606 /* Casting avoids a GCC warning. */
7468 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg); 7607 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg);
7469 7608
7470 /* Put the image into the pixmap, then free the X image and its buffer. */ 7609 /* Put ximg into the image. */
7471 x_put_x_image (f, ximg, img->pixmap, width, height); 7610 image_put_x_image (f, img, ximg, 0);
7472 x_destroy_x_image (ximg);
7473 7611
7474 return 1; 7612 return 1;
7475} 7613}
@@ -7489,6 +7627,76 @@ gif_load (struct frame *f, struct image *img)
7489#endif /* HAVE_GIF */ 7627#endif /* HAVE_GIF */
7490 7628
7491 7629
7630static void
7631compute_image_size (size_t width, size_t height,
7632 Lisp_Object spec,
7633 int *d_width, int *d_height)
7634{
7635 Lisp_Object value;
7636 int desired_width, desired_height;
7637
7638 /* If width and/or height is set in the display spec assume we want
7639 to scale to those values. If either h or w is unspecified, the
7640 unspecified should be calculated from the specified to preserve
7641 aspect ratio. */
7642 value = image_spec_value (spec, QCwidth, NULL);
7643 desired_width = (INTEGERP (value) ? XFASTINT (value) : -1);
7644 value = image_spec_value (spec, QCheight, NULL);
7645 desired_height = (INTEGERP (value) ? XFASTINT (value) : -1);
7646
7647 if (desired_width == -1)
7648 {
7649 value = image_spec_value (spec, QCmax_width, NULL);
7650 if (INTEGERP (value) &&
7651 width > XFASTINT (value))
7652 {
7653 /* The image is wider than :max-width. */
7654 desired_width = XFASTINT (value);
7655 if (desired_height == -1)
7656 {
7657 value = image_spec_value (spec, QCmax_height, NULL);
7658 if (INTEGERP (value))
7659 {
7660 /* We have no specified height, but we have a
7661 :max-height value, so check that we satisfy both
7662 conditions. */
7663 desired_height = (double) desired_width / width * height;
7664 if (desired_height > XFASTINT (value))
7665 {
7666 desired_height = XFASTINT (value);
7667 desired_width = (double) desired_height / height * width;
7668 }
7669 }
7670 else
7671 {
7672 /* We have no specified height and no specified
7673 max-height, so just compute the height. */
7674 desired_height = (double) desired_width / width * height;
7675 }
7676 }
7677 }
7678 }
7679
7680 if (desired_height == -1)
7681 {
7682 value = image_spec_value (spec, QCmax_height, NULL);
7683 if (INTEGERP (value) &&
7684 height > XFASTINT (value))
7685 desired_height = XFASTINT (value);
7686 }
7687
7688 if (desired_width != -1 && desired_height == -1)
7689 /* w known, calculate h. */
7690 desired_height = (double) desired_width / width * height;
7691
7692 if (desired_width == -1 && desired_height != -1)
7693 /* h known, calculate w. */
7694 desired_width = (double) desired_height / height * width;
7695
7696 *d_width = desired_width;
7697 *d_height = desired_height;
7698}
7699
7492/*********************************************************************** 7700/***********************************************************************
7493 ImageMagick 7701 ImageMagick
7494***********************************************************************/ 7702***********************************************************************/
@@ -7516,6 +7724,8 @@ enum imagemagick_keyword_index
7516 IMAGEMAGICK_BACKGROUND, 7724 IMAGEMAGICK_BACKGROUND,
7517 IMAGEMAGICK_HEIGHT, 7725 IMAGEMAGICK_HEIGHT,
7518 IMAGEMAGICK_WIDTH, 7726 IMAGEMAGICK_WIDTH,
7727 IMAGEMAGICK_MAX_HEIGHT,
7728 IMAGEMAGICK_MAX_WIDTH,
7519 IMAGEMAGICK_ROTATION, 7729 IMAGEMAGICK_ROTATION,
7520 IMAGEMAGICK_CROP, 7730 IMAGEMAGICK_CROP,
7521 IMAGEMAGICK_LAST 7731 IMAGEMAGICK_LAST
@@ -7538,6 +7748,8 @@ static struct image_keyword imagemagick_format[IMAGEMAGICK_LAST] =
7538 {":background", IMAGE_STRING_OR_NIL_VALUE, 0}, 7748 {":background", IMAGE_STRING_OR_NIL_VALUE, 0},
7539 {":height", IMAGE_INTEGER_VALUE, 0}, 7749 {":height", IMAGE_INTEGER_VALUE, 0},
7540 {":width", IMAGE_INTEGER_VALUE, 0}, 7750 {":width", IMAGE_INTEGER_VALUE, 0},
7751 {":max-height", IMAGE_INTEGER_VALUE, 0},
7752 {":max-width", IMAGE_INTEGER_VALUE, 0},
7541 {":rotation", IMAGE_NUMBER_VALUE, 0}, 7753 {":rotation", IMAGE_NUMBER_VALUE, 0},
7542 {":crop", IMAGE_DONT_CHECK_VALUE_TYPE, 0} 7754 {":crop", IMAGE_DONT_CHECK_VALUE_TYPE, 0}
7543 }; 7755 };
@@ -7726,24 +7938,10 @@ imagemagick_load_image (struct frame *f, struct image *img,
7726 PixelSetBlue (bg_wand, (double) bgcolor.blue / 65535); 7938 PixelSetBlue (bg_wand, (double) bgcolor.blue / 65535);
7727 } 7939 }
7728 7940
7729 /* If width and/or height is set in the display spec assume we want 7941 compute_image_size (MagickGetImageWidth (image_wand),
7730 to scale to those values. If either h or w is unspecified, the 7942 MagickGetImageHeight (image_wand),
7731 unspecified should be calculated from the specified to preserve 7943 img->spec, &desired_width, &desired_height);
7732 aspect ratio. */
7733 value = image_spec_value (img->spec, QCwidth, NULL);
7734 desired_width = (INTEGERP (value) ? XFASTINT (value) : -1);
7735 value = image_spec_value (img->spec, QCheight, NULL);
7736 desired_height = (INTEGERP (value) ? XFASTINT (value) : -1);
7737
7738 height = MagickGetImageHeight (image_wand);
7739 width = MagickGetImageWidth (image_wand);
7740 7944
7741 if (desired_width != -1 && desired_height == -1)
7742 /* w known, calculate h. */
7743 desired_height = (double) desired_width / width * height;
7744 if (desired_width == -1 && desired_height != -1)
7745 /* h known, calculate w. */
7746 desired_width = (double) desired_height / height * width;
7747 if (desired_width != -1 && desired_height != -1) 7945 if (desired_width != -1 && desired_height != -1)
7748 { 7946 {
7749 status = MagickScaleImage (image_wand, desired_width, desired_height); 7947 status = MagickScaleImage (image_wand, desired_width, desired_height);
@@ -7847,8 +8045,8 @@ imagemagick_load_image (struct frame *f, struct image *img,
7847 int imagedepth = 24; /*MagickGetImageDepth(image_wand);*/ 8045 int imagedepth = 24; /*MagickGetImageDepth(image_wand);*/
7848 const char *exportdepth = imagedepth <= 8 ? "I" : "BGRP"; /*"RGBP";*/ 8046 const char *exportdepth = imagedepth <= 8 ? "I" : "BGRP"; /*"RGBP";*/
7849 /* Try to create a x pixmap to hold the imagemagick pixmap. */ 8047 /* Try to create a x pixmap to hold the imagemagick pixmap. */
7850 if (!x_create_x_image_and_pixmap (f, width, height, imagedepth, 8048 if (!image_create_x_image_and_pixmap (f, img, width, height, imagedepth,
7851 &ximg, &img->pixmap)) 8049 &ximg, 0))
7852 { 8050 {
7853#ifdef COLOR_TABLE_SUPPORT 8051#ifdef COLOR_TABLE_SUPPORT
7854 free_color_table (); 8052 free_color_table ();
@@ -7886,8 +8084,8 @@ imagemagick_load_image (struct frame *f, struct image *img,
7886 size_t image_height; 8084 size_t image_height;
7887 8085
7888 /* Try to create a x pixmap to hold the imagemagick pixmap. */ 8086 /* Try to create a x pixmap to hold the imagemagick pixmap. */
7889 if (!x_create_x_image_and_pixmap (f, width, height, 0, 8087 if (!image_create_x_image_and_pixmap (f, img, width, height, 0,
7890 &ximg, &img->pixmap)) 8088 &ximg, 0))
7891 { 8089 {
7892#ifdef COLOR_TABLE_SUPPORT 8090#ifdef COLOR_TABLE_SUPPORT
7893 free_color_table (); 8091 free_color_table ();
@@ -7941,10 +8139,8 @@ imagemagick_load_image (struct frame *f, struct image *img,
7941 img->width = width; 8139 img->width = width;
7942 img->height = height; 8140 img->height = height;
7943 8141
7944 /* Put the image into the pixmap, then free the X image and its 8142 /* Put ximg into the image. */
7945 buffer. */ 8143 image_put_x_image (f, img, ximg, 0);
7946 x_put_x_image (f, ximg, img->pixmap, width, height);
7947 x_destroy_x_image (ximg);
7948 8144
7949 /* Final cleanup. image_wand should be the only resource left. */ 8145 /* Final cleanup. image_wand should be the only resource left. */
7950 DestroyMagickWand (image_wand); 8146 DestroyMagickWand (image_wand);
@@ -8338,7 +8534,7 @@ svg_load_image (struct frame *f, /* Pointer to emacs frame structure. *
8338 eassert (fn_gdk_pixbuf_get_bits_per_sample (pixbuf) == 8); 8534 eassert (fn_gdk_pixbuf_get_bits_per_sample (pixbuf) == 8);
8339 8535
8340 /* Try to create a x pixmap to hold the svg pixmap. */ 8536 /* Try to create a x pixmap to hold the svg pixmap. */
8341 if (!x_create_x_image_and_pixmap (f, width, height, 0, &ximg, &img->pixmap)) 8537 if (!image_create_x_image_and_pixmap (f, img, width, height, 0, &ximg, 0))
8342 { 8538 {
8343 fn_g_object_unref (pixbuf); 8539 fn_g_object_unref (pixbuf);
8344 return 0; 8540 return 0;
@@ -8413,10 +8609,8 @@ svg_load_image (struct frame *f, /* Pointer to emacs frame structure. *
8413 Casting avoids a GCC warning. */ 8609 Casting avoids a GCC warning. */
8414 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg); 8610 IMAGE_BACKGROUND (img, f, (XImagePtr_or_DC)ximg);
8415 8611
8416 /* Put the image into the pixmap, then free the X image and its 8612 /* Put ximg into the image. */
8417 buffer. */ 8613 image_put_x_image (f, img, ximg, 0);
8418 x_put_x_image (f, ximg, img->pixmap, width, height);
8419 x_destroy_x_image (ximg);
8420 8614
8421 return 1; 8615 return 1;
8422 8616
@@ -8895,6 +9089,8 @@ non-numeric, there is no explicit limit on the size of images. */);
8895 DEFSYM (Qheuristic, "heuristic"); 9089 DEFSYM (Qheuristic, "heuristic");
8896 9090
8897 DEFSYM (Qpostscript, "postscript"); 9091 DEFSYM (Qpostscript, "postscript");
9092 DEFSYM (QCmax_width, ":max-width");
9093 DEFSYM (QCmax_height, ":max-height");
8898#ifdef HAVE_GHOSTSCRIPT 9094#ifdef HAVE_GHOSTSCRIPT
8899 ADD_IMAGE_TYPE (Qpostscript); 9095 ADD_IMAGE_TYPE (Qpostscript);
8900 DEFSYM (QCloader, ":loader"); 9096 DEFSYM (QCloader, ":loader");