fixed rotated image for pets and product as well

This commit is contained in:
Alex
2026-04-13 00:30:26 -06:00
parent d85530dd2c
commit fba042d2b9
2 changed files with 77 additions and 6 deletions

View File

@@ -380,7 +380,7 @@ public class PetController {
setGraphic(null);
return;
}
DesktopImageSupport.loadImageInto(imageView, item, 24, 24);
DesktopImageSupport.loadImageInto(imageView, item, 48, 48);
setGraphic(container);
}
});

View File

@@ -12,6 +12,7 @@ import java.util.concurrent.ConcurrentHashMap;
public final class DesktopImageSupport {
private static final Map<String, Image> IMAGE_CACHE = new ConcurrentHashMap<>();
private static final Map<String, Integer> ORIENTATION_CACHE = new ConcurrentHashMap<>();
private DesktopImageSupport() {
}
@@ -22,32 +23,49 @@ public final class DesktopImageSupport {
imageView.setPreserveRatio(true);
imageView.setSmooth(true);
imageView.setImage(null);
imageView.setRotate(0);
if (imageUrl == null || imageUrl.isBlank()) {
return;
}
if (imageUrl.startsWith("file:")) {
Image image = new Image(imageUrl, 0, 0, true, true);
if (!image.isError()) {
imageView.setImage(image);
}
new Thread(() -> {
try {
byte[] bytes = java.net.URI.create(imageUrl).toURL().openStream().readAllBytes();
int orientation = readExifOrientation(bytes);
Image image = new Image(new ByteArrayInputStream(bytes));
if (!image.isError()) {
Platform.runLater(() -> {
imageView.setImage(image);
imageView.setRotate(exifOrientationToAngle(orientation));
});
}
} catch (Exception ignored) {
}
}, "desktop-image-loader").start();
return;
}
Image cached = IMAGE_CACHE.get(imageUrl);
if (cached != null) {
imageView.setImage(cached);
imageView.setRotate(exifOrientationToAngle(ORIENTATION_CACHE.getOrDefault(imageUrl, 1)));
return;
}
new Thread(() -> {
try {
byte[] bytes = ApiClient.getInstance().getBytes(imageUrl);
int orientation = readExifOrientation(bytes);
Image image = new Image(new ByteArrayInputStream(bytes));
if (!image.isError()) {
IMAGE_CACHE.put(imageUrl, image);
Platform.runLater(() -> imageView.setImage(image));
ORIENTATION_CACHE.put(imageUrl, orientation);
Platform.runLater(() -> {
imageView.setImage(image);
imageView.setRotate(exifOrientationToAngle(orientation));
});
}
} catch (Exception ignored) {
}
@@ -57,6 +75,59 @@ public final class DesktopImageSupport {
public static void evict(String imageUrl) {
if (imageUrl != null && !imageUrl.isBlank()) {
IMAGE_CACHE.remove(imageUrl);
ORIENTATION_CACHE.remove(imageUrl);
}
}
private static double exifOrientationToAngle(int orientation) {
return switch (orientation) {
case 3 -> 180;
case 6 -> 90;
case 8 -> -90;
default -> 0;
};
}
private static int readExifOrientation(byte[] data) {
try {
if (data.length < 2 || (data[0] & 0xFF) != 0xFF || (data[1] & 0xFF) != 0xD8) return 1;
int offset = 2;
while (offset + 4 < data.length) {
if ((data[offset] & 0xFF) != 0xFF) break;
int marker = data[offset + 1] & 0xFF;
int segLen = ((data[offset + 2] & 0xFF) << 8) | (data[offset + 3] & 0xFF);
if (marker == 0xE1 && offset + 9 < data.length
&& data[offset + 4] == 'E' && data[offset + 5] == 'x'
&& data[offset + 6] == 'i' && data[offset + 7] == 'f'
&& data[offset + 8] == 0 && data[offset + 9] == 0) {
int tiff = offset + 10;
boolean le = data[tiff] == 'I';
int ifdOffset = readInt(data, tiff + 4, le);
int ifd = tiff + ifdOffset;
int entries = readShort(data, ifd, le);
for (int i = 0; i < entries; i++) {
int e = ifd + 2 + i * 12;
if (e + 9 < data.length && readShort(data, e, le) == 0x0112) {
return readShort(data, e + 8, le);
}
}
}
if (marker == 0xDA) break;
offset += 2 + segLen;
}
} catch (Exception ignored) {}
return 1;
}
private static int readShort(byte[] data, int offset, boolean le) {
return le
? (data[offset] & 0xFF) | ((data[offset + 1] & 0xFF) << 8)
: ((data[offset] & 0xFF) << 8) | (data[offset + 1] & 0xFF);
}
private static int readInt(byte[] data, int offset, boolean le) {
return le
? (data[offset] & 0xFF) | ((data[offset + 1] & 0xFF) << 8) | ((data[offset + 2] & 0xFF) << 16) | ((data[offset + 3] & 0xFF) << 24)
: ((data[offset] & 0xFF) << 24) | ((data[offset + 1] & 0xFF) << 16) | ((data[offset + 2] & 0xFF) << 8) | (data[offset + 3] & 0xFF);
}
}