diff options
| author | Lars Ingebrigtsen | 2017-07-15 02:45:19 +0200 |
|---|---|---|
| committer | Lars Ingebrigtsen | 2017-07-15 02:48:17 +0200 |
| commit | ae56c9674b4668ded392c66d46aa22db902ddd71 (patch) | |
| tree | 3472b1e2c5877ee37a0b4813f60bc2b2b5515d47 /src/image.c | |
| parent | 89c5d59280edaf89b959597a39d848b54c36975a (diff) | |
| download | emacs-ae56c9674b4668ded392c66d46aa22db902ddd71.tar.gz emacs-ae56c9674b4668ded392c66d46aa22db902ddd71.zip | |
Make combinations of :width/:max-height image specs work reliably
* doc/lispref/display.texi (ImageMagick Images): Document
:width/:max-height combinations (etc) (bug #25583).
* src/image.c (compute_image_size): Handle :width/:max-height
(etc) combinations consistently (by letting "max" win and
preserve ratio).
* test/manual/image-size-tests.el (image-size-tests): Add
tests for :width/:max-height (etc) combinations.
Diffstat (limited to 'src/image.c')
| -rw-r--r-- | src/image.c | 97 |
1 files changed, 45 insertions, 52 deletions
diff --git a/src/image.c b/src/image.c index 1426e309445..69a529e8c35 100644 --- a/src/image.c +++ b/src/image.c | |||
| @@ -8086,83 +8086,76 @@ compute_image_size (size_t width, size_t height, | |||
| 8086 | int *d_width, int *d_height) | 8086 | int *d_width, int *d_height) |
| 8087 | { | 8087 | { |
| 8088 | Lisp_Object value; | 8088 | Lisp_Object value; |
| 8089 | int desired_width, desired_height; | 8089 | int desired_width = -1, desired_height = -1, max_width = -1, max_height = -1; |
| 8090 | double scale = 1; | 8090 | double scale = 1; |
| 8091 | 8091 | ||
| 8092 | value = image_spec_value (spec, QCscale, NULL); | 8092 | value = image_spec_value (spec, QCscale, NULL); |
| 8093 | if (NUMBERP (value)) | 8093 | if (NUMBERP (value)) |
| 8094 | scale = XFLOATINT (value); | 8094 | scale = XFLOATINT (value); |
| 8095 | 8095 | ||
| 8096 | value = image_spec_value (spec, QCmax_width, NULL); | ||
| 8097 | if (NATNUMP (value)) | ||
| 8098 | max_width = min (XFASTINT (value), INT_MAX); | ||
| 8099 | |||
| 8100 | value = image_spec_value (spec, QCmax_height, NULL); | ||
| 8101 | if (NATNUMP (value)) | ||
| 8102 | max_height = min (XFASTINT (value), INT_MAX); | ||
| 8103 | |||
| 8096 | /* If width and/or height is set in the display spec assume we want | 8104 | /* If width and/or height is set in the display spec assume we want |
| 8097 | to scale to those values. If either h or w is unspecified, the | 8105 | to scale to those values. If either h or w is unspecified, the |
| 8098 | unspecified should be calculated from the specified to preserve | 8106 | unspecified should be calculated from the specified to preserve |
| 8099 | aspect ratio. */ | 8107 | aspect ratio. */ |
| 8100 | value = image_spec_value (spec, QCwidth, NULL); | 8108 | value = image_spec_value (spec, QCwidth, NULL); |
| 8101 | desired_width = NATNUMP (value) ? | 8109 | if (NATNUMP (value)) |
| 8102 | min (XFASTINT (value) * scale, INT_MAX) : -1; | ||
| 8103 | value = image_spec_value (spec, QCheight, NULL); | ||
| 8104 | desired_height = NATNUMP (value) ? | ||
| 8105 | min (XFASTINT (value) * scale, INT_MAX) : -1; | ||
| 8106 | |||
| 8107 | width = width * scale; | ||
| 8108 | height = height * scale; | ||
| 8109 | |||
| 8110 | if (desired_width == -1) | ||
| 8111 | { | 8110 | { |
| 8112 | value = image_spec_value (spec, QCmax_width, NULL); | 8111 | desired_width = min (XFASTINT (value) * scale, INT_MAX); |
| 8113 | if (NATNUMP (value)) | 8112 | /* :width overrides :max-width. */ |
| 8114 | { | 8113 | max_width = -1; |
| 8115 | int max_width = min (XFASTINT (value), INT_MAX); | ||
| 8116 | if (max_width < width) | ||
| 8117 | { | ||
| 8118 | /* The image is wider than :max-width. */ | ||
| 8119 | desired_width = max_width; | ||
| 8120 | if (desired_height == -1) | ||
| 8121 | { | ||
| 8122 | desired_height = scale_image_size (desired_width, | ||
| 8123 | width, height); | ||
| 8124 | value = image_spec_value (spec, QCmax_height, NULL); | ||
| 8125 | if (NATNUMP (value)) | ||
| 8126 | { | ||
| 8127 | int max_height = min (XFASTINT (value), INT_MAX); | ||
| 8128 | if (max_height < desired_height) | ||
| 8129 | { | ||
| 8130 | desired_height = max_height; | ||
| 8131 | desired_width = scale_image_size (desired_height, | ||
| 8132 | height, width); | ||
| 8133 | } | ||
| 8134 | } | ||
| 8135 | } | ||
| 8136 | } | ||
| 8137 | } | ||
| 8138 | } | 8114 | } |
| 8139 | 8115 | ||
| 8140 | if (desired_height == -1) | 8116 | value = image_spec_value (spec, QCheight, NULL); |
| 8117 | if (NATNUMP (value)) | ||
| 8141 | { | 8118 | { |
| 8142 | value = image_spec_value (spec, QCmax_height, NULL); | 8119 | desired_height = min (XFASTINT (value) * scale, INT_MAX); |
| 8143 | if (NATNUMP (value)) | 8120 | /* :height overrides :max-height. */ |
| 8144 | { | 8121 | max_height = -1; |
| 8145 | int max_height = min (XFASTINT (value), INT_MAX); | ||
| 8146 | if (max_height < height) | ||
| 8147 | desired_height = max_height; | ||
| 8148 | } | ||
| 8149 | } | 8122 | } |
| 8150 | 8123 | ||
| 8124 | /* If we have both width/height set explicitly, we skip past all the | ||
| 8125 | aspect ratio-preserving computations below. */ | ||
| 8126 | if (desired_width != -1 && desired_height != -1) | ||
| 8127 | goto out; | ||
| 8128 | |||
| 8129 | width = width * scale; | ||
| 8130 | height = height * scale; | ||
| 8131 | |||
| 8151 | if (desired_width != -1 && desired_height == -1) | 8132 | if (desired_width != -1 && desired_height == -1) |
| 8152 | /* w known, calculate h. */ | 8133 | /* Width known, calculate height. */ |
| 8153 | desired_height = scale_image_size (desired_width, width, height); | 8134 | desired_height = scale_image_size (desired_width, width, height); |
| 8154 | 8135 | else if (desired_width == -1 && desired_height != -1) | |
| 8155 | if (desired_width == -1 && desired_height != -1) | 8136 | /* Height known, calculate width. */ |
| 8156 | /* h known, calculate w. */ | ||
| 8157 | desired_width = scale_image_size (desired_height, height, width); | 8137 | desired_width = scale_image_size (desired_height, height, width); |
| 8158 | 8138 | else | |
| 8159 | /* We have no width/height settings, so just apply the scale. */ | ||
| 8160 | if (desired_width == -1 && desired_height == -1) | ||
| 8161 | { | 8139 | { |
| 8162 | desired_width = width; | 8140 | desired_width = width; |
| 8163 | desired_height = height; | 8141 | desired_height = height; |
| 8164 | } | 8142 | } |
| 8165 | 8143 | ||
| 8144 | if (max_width != -1 && desired_width > max_width) | ||
| 8145 | { | ||
| 8146 | /* The image is wider than :max-width. */ | ||
| 8147 | desired_width = max_width; | ||
| 8148 | desired_height = scale_image_size (desired_width, width, height); | ||
| 8149 | } | ||
| 8150 | |||
| 8151 | if (max_height != -1 && desired_height > max_height) | ||
| 8152 | { | ||
| 8153 | /* The image is higher than :max-height. */ | ||
| 8154 | desired_height = max_height; | ||
| 8155 | desired_width = scale_image_size (desired_height, height, width); | ||
| 8156 | } | ||
| 8157 | |||
| 8158 | out: | ||
| 8166 | *d_width = desired_width; | 8159 | *d_width = desired_width; |
| 8167 | *d_height = desired_height; | 8160 | *d_height = desired_height; |
| 8168 | } | 8161 | } |