source: josm/trunk/src/org/openstreetmap/josm/tools/ImageResizeMode.java@ 17144

Last change on this file since 17144 was 17144, checked in by simon04, 4 years ago

fix #19751 - MapImage.rescale: use original SVG instead of rastered version

File size: 5.2 KB
Line 
1// License: GPL. For details, see LICENSE file.
2package org.openstreetmap.josm.tools;
3
4import java.awt.Dimension;
5import java.awt.Graphics2D;
6import java.awt.Image;
7import java.awt.RenderingHints;
8import java.awt.image.BufferedImage;
9import java.util.function.Consumer;
10
11/**
12 * Determines how the image is sized/resized in {@link ImageResource#getImageIcon(Dimension, boolean, ImageResizeMode)}.
13 */
14enum ImageResizeMode {
15
16 /**
17 * Calculate proportional dimensions that best fit into the target width and height, retain aspect ratio
18 */
19 AUTO {
20 @Override
21 Dimension computeDimension(Dimension dim, Dimension icon) {
22 CheckParameterUtil.ensureThat((dim.width > 0 || dim.width == -1) && (dim.height > 0 || dim.height == -1),
23 () -> dim + " is invalid");
24 if (dim.width == -1 && dim.height == -1) {
25 return new Dimension(GuiSizesHelper.getSizeDpiAdjusted(icon.width), GuiSizesHelper.getSizeDpiAdjusted(icon.height));
26 } else if (dim.width == -1) {
27 return new Dimension(Math.max(1, icon.width * dim.height / icon.height), dim.height);
28 } else if (dim.height == -1) {
29 return new Dimension(dim.width, Math.max(1, icon.height * dim.width / icon.width));
30 } else if (icon.getWidth() / dim.getWidth() > icon.getHeight() / dim.getHeight()) {
31 return computeDimension(new Dimension(dim.width, -1), icon);
32 } else {
33 return computeDimension(new Dimension(-1, dim.height), icon);
34 }
35 }
36 },
37
38 /**
39 * Calculate dimensions for the largest image that fit within the bounding box, retain aspect ratio
40 */
41 BOUNDED {
42 @Override
43 Dimension computeDimension(Dimension dim, Dimension icon) {
44 CheckParameterUtil.ensureThat((dim.width > 0 || dim.width == -1) && (dim.height > 0 || dim.height == -1),
45 () -> dim + " is invalid");
46 final int maxWidth = Math.min(dim.width, icon.width);
47 final int maxHeight = Math.min(dim.height, icon.height);
48 return AUTO.computeDimension(new Dimension(maxWidth, maxHeight), icon);
49 }
50 },
51
52 /**
53 * Position an appropriately scaled image within the bounding box, retain aspect ratio
54 */
55 PADDED {
56 @Override
57 Dimension computeDimension(Dimension dim, Dimension icon) {
58 CheckParameterUtil.ensureThat(dim.width > 0 && dim.height > 0, () -> dim + " is invalid");
59 return dim;
60 }
61
62 @Override
63 void prepareGraphics(Dimension icon, BufferedImage image, Graphics2D g) {
64 g.setClip(0, 0, image.getWidth(), image.getHeight());
65 final double scale = Math.min(image.getWidth() / icon.getWidth(), image.getHeight() / icon.getHeight());
66 g.translate((image.getWidth() - icon.getWidth() * scale) / 2, (image.getHeight() - icon.getHeight() * scale) / 2);
67 g.scale(scale, scale);
68 }
69 };
70
71 /**
72 * Computes the dimension for the resulting image
73 * @param dim the desired image dimension
74 * @param icon the dimensions of the image to resize
75 * @return the dimension for the resulting image
76 */
77 abstract Dimension computeDimension(Dimension dim, Dimension icon);
78
79 /**
80 * Creates a new buffered image and applies the rendering function
81 * @param dim the desired image dimension
82 * @param icon the dimensions of the image to resize
83 * @param renderer the rendering function
84 * @param sourceIcon the source icon to draw
85 * @return a new buffered image
86 * @throws IllegalArgumentException if renderer or sourceIcon is null
87 */
88 BufferedImage createBufferedImage(Dimension dim, Dimension icon, Consumer<Graphics2D> renderer, Image sourceIcon) {
89 final Dimension real = computeDimension(dim, icon);
90 final BufferedImage bufferedImage = new BufferedImage(real.width, real.height, BufferedImage.TYPE_INT_ARGB);
91 final Graphics2D g = bufferedImage.createGraphics();
92 g.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
93 if (renderer != null) {
94 prepareGraphics(icon, bufferedImage, g);
95 renderer.accept(g);
96 } else if (sourceIcon != null) {
97 sourceIcon = sourceIcon.getScaledInstance(real.width, real.height, Image.SCALE_SMOOTH);
98 g.drawImage(sourceIcon, 0, 0, null);
99 } else {
100 throw new IllegalArgumentException("renderer or sourceIcon");
101 }
102 return bufferedImage;
103 }
104
105 /**
106 * Prepares the graphics object for rendering the given image
107 * @param icon the dimensions of the image to resize
108 * @param image the image to render afterwards
109 * @param g graphics
110 */
111 void prepareGraphics(Dimension icon, BufferedImage image, Graphics2D g) {
112 g.setClip(0, 0, image.getWidth(), image.getHeight());
113 g.scale(image.getWidth() / icon.getWidth(), image.getHeight() / icon.getHeight());
114 }
115
116 /**
117 * Returns a cache key for this mode and the given dimension
118 * @param dim the desired image dimension
119 * @return a cache key
120 */
121 int cacheKey(Dimension dim) {
122 return (ordinal() << 28) | ((dim.width & 0xfff) << 16) | (dim.height & 0xfff);
123 }
124
125}
Note: See TracBrowser for help on using the repository browser.