如何在 Java 中检测用户是否有视网膜显示屏?我已经知道使用检测比例因子Toolkit.getDefaultToolkit().getDesktopProperty("apple.awt.contentScaleFactor")
,但是java不会让我将返回值转换为int。我想知道如何将其转换为 int,或另一种检测视网膜显示器的方法。
当心用户可能有多个显示器!在这种情况下,“检测 Retina 显示屏”意味着什么?
对于大多数目的,您有兴趣将图像渲染到 GUI 组件上。因此您需要检测组件所在的显示器.
Luckily java.awt.Component
has a getGraphicsConfiguration method这为我们提供了必要的信息。
但是,Java 8(和 7)和 Java 9 需要不同的处理:Java 9 直接通过图形设备的默认变换。 Java 7 和 8 也公开了此转换,但它始终设置为身份转换(即无转换),即使对于 Retina 显示器也是如此。
对于 Java
以下类实现了对 Retina 显示的必要检查,并且适用于 Java 8 和 Java 9。Java 7 也可能适用于细微的更改,但我没有测试它。
package me.klmr.ui;
import java.awt.*;
import java.lang.reflect.Method;
public final class Device {
private enum JavaVersion {
V8,
V9
}
private static final JavaVersion JAVA_VERSION = getJavaVersion();
private static JavaVersion getJavaVersion() {
final String versionString = System.getProperty("java.version");
if (versionString.startsWith("1.8")) return JavaVersion.V8;
if (versionString.startsWith("9.")) return JavaVersion.V9;
throw new RuntimeException("Unsupported Java version");
}
public static GraphicsConfiguration getCurrentConfiguration(final Component component) {
final GraphicsConfiguration graphicsConfiguration = component.getGraphicsConfiguration();
if (graphicsConfiguration == null) {
return GraphicsEnvironment.getLocalGraphicsEnvironment().getDefaultScreenDevice().getDefaultConfiguration();
} else {
return graphicsConfiguration;
}
}
public static GraphicsDevice getCurrentDevice(final Component component) {
final GraphicsConfiguration graphicsConfiguration = component.getGraphicsConfiguration();
if (graphicsConfiguration == null) {
return GraphicsEnvironment.getLocalGraphicsEnvironment().getDefaultScreenDevice();
} else {
return graphicsConfiguration.getDevice();
}
}
public static boolean isOnRetinaDisplay(final Component component) {
switch (JAVA_VERSION) {
case V8: return isOnRetinaDisplayJava8(component);
case V9: return isOnRetinaDisplayJava9(component);
default: throw new AssertionError("Unreachable");
}
}
public static double getDisplayScalingFactor(final Component component) {
switch (JAVA_VERSION) {
case V8: return getDisplayScalingFactorJava8(component);
case V9: return getDisplayScalingFactorJava9(component);
default: throw new AssertionError("Unreachable");
}
}
private static boolean isOnRetinaDisplayJava8(final Component component) {
final GraphicsDevice device = getCurrentDevice(component);
try {
final Method getScaleFactorMethod = device.getClass().getMethod("getScaleFactor");
final Object scale = getScaleFactorMethod.invoke(device);
return scale instanceof Integer && ((Integer) scale).intValue() == 2;
} catch (ReflectiveOperationException e) {
return false;
}
}
private static boolean isOnRetinaDisplayJava9(final Component component) {
return ! getCurrentConfiguration(component).getDefaultTransform().isIdentity();
}
private static double getDisplayScalingFactorJava8(final Component component) {
return isOnRetinaDisplayJava8(component) ? 2.0 : 1.0;
}
private static double getDisplayScalingFactorJava9(final Component component) {
return getCurrentConfiguration(component).getDefaultTransform().getScaleX();
}
}
实际上,将对话框从一个屏幕移动到另一个屏幕将导致组件重新渲染。如果组件的渲染代码使用上面的类来找出正确的分辨率,那么无论它们当前位于哪个显示器上,它们都将正确渲染。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)