You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何修复GraphicsEnvironment.getRefreshRate()返回错误刷新率的问题

Java获取Linux显示器刷新率错误问题排查与修复

问题现象

在配备单台165Hz显示器的Manjaro台式机上,通过Java GraphicsEnvironment类获取主显示器刷新率时返回50,而非正确的165;但在搭载60Hz显示器的Linux Mint笔记本上结果正常。

测试代码

import java.awt.GraphicsEnvironment;

class FileName {
    public static void main(String[] args) {
        int hrz = GraphicsEnvironment.getLocalGraphicsEnvironment().getScreenDevices()[0].getDisplayMode().getRefreshRate();

        System.out.println(hrz);
    }
}

运行输出

[shringe@dashingkoso Refresh-Rate]$ javac FileName.java
[shringe@dashingkoso Refresh-Rate]$ java FileName
50
[shringe@dashingkoso Refresh-Rate]$ 

系统显示模式确认(xrandr -q输出)

DP-0 connected primary 2560x1440+0+0 (normal left inverted right x axis y axis) 597mm x 336mm
   2560x1440     59.95 + 165.00*  160.00   155.00   143.97   120.00  
   1920x1080    119.88   100.00    60.00    59.94    50.00  
   1440x900      59.89  
   1440x576      50.00  
   1280x1024     75.02    60.02  
   1152x864      75.00  
   1024x768      75.03    70.07    60.00  
   800x600       75.00    72.19    60.32    56.25  
   640x480       75.00    72.81    59.94

原因分析

  • Java AWT的getRefreshRate()方法在Linux环境下依赖X11的旧接口实现,这类接口对高刷新率显示器的支持存在缺陷,可能错误读取非当前激活模式的参数(比如误取了1080p分辨率下的50Hz值)。
  • Manjaro搭配的桌面环境(如KDE/GNOME)与显卡驱动的组合,可能导致AWT无法正确同步显示器的实际运行模式,尤其是当显示器支持多档刷新率选项时。

修复方法

1. 解析xrandr命令输出

直接调用系统xrandr -q命令,解析带*标记的当前激活模式刷新率,绕过AWT的局限性:

import java.io.BufferedReader;
import java.io.InputStreamReader;

class RefreshRateFix {
    public static void main(String[] args) {
        try {
            Process process = Runtime.getRuntime().exec("xrandr -q");
            BufferedReader reader = new BufferedReader(new InputStreamReader(process.getInputStream()));
            String line;
            while ((line = reader.readLine()) != null) {
                if (line.contains("primary") && line.contains("*")) {
                    String[] parts = line.split("\\s+");
                    for (String part : parts) {
                        if (part.contains("*")) {
                            String rateStr = part.replace("*", "");
                            int rate = (int) Math.round(Double.parseDouble(rateStr));
                            System.out.println(rate);
                            break;
                        }
                    }
                    break;
                }
            }
            reader.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

2. 使用JavaFX的Screen API

JavaFX的Screen类对Linux显示器的兼容性更好,能正确读取当前刷新率:

import javafx.stage.Screen;

class FXRefreshRate {
    public static void main(String[] args) {
        double rate = Screen.getPrimary().getRefreshRate();
        System.out.println((int) Math.round(rate));
    }
}

注意:运行JavaFX代码需确保环境包含JavaFX库,或采用模块化编译运行方式。

3. 升级JDK版本

部分旧版本JDK的AWT实现存在该bug,升级至最新的OpenJDK或Oracle JDK版本,可能已修复Linux下高刷新率识别问题。

内容的提问来源于stack exchange,提问作者Shringe_

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.27 22:42:52