JavaFX 警告:不支持的 JavaFX 配置:类是从“未命名模块@..."加载的 [英] JavaFX WARNING: Unsupported JavaFX configuration: classes were loaded from 'unnamed module @...'

查看:89
本文介绍了JavaFX 警告:不支持的 JavaFX 配置:类是从“未命名模块@..."加载的的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我刚刚下载了 JavaFX 并进行了设置,其他什么都没做.我运行了示例代码,这是弹出的警告,尽管一切都已编译.我正在使用 IntelliJ.

I just downloaded JavaFX and set it up, I have done nothing else. I ran the sample code and this was the warning that popped up, although everything compiled. I'm using IntelliJ.

这是在 Main.java 中:

This is in Main.java:

package sample;

import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.scene.Parent;
import javafx.scene.Scene;
import javafx.stage.Stage;

public class Main extends Application {

    @Override
    public void start(Stage primaryStage) throws Exception{
        Parent root = FXMLLoader.load(getClass().getResource("sample.fxml"));
        primaryStage.setTitle("Hello World");
        primaryStage.setScene(new Scene(root, 300, 275));
        primaryStage.show();
    }


    public static void main(String[] args) {
        launch(args);
    }
}

这是在 sample.fxml 中:

This is in sample.fxml:

<?import javafx.geometry.Insets?>
<?import javafx.scene.layout.GridPane?>

<?import javafx.scene.control.Button?>
<?import javafx.scene.control.Label?>
<GridPane fx:controller="sample.Controller"
          xmlns:fx="http://javafx.com/fxml" alignment="center" hgap="10" vgap="10">
</GridPane>

运行时,一切都编译,弹出窗口,但我收到标题中所述的警告.

When running, everything compiles, the window pops up, but I get the warning as stated in the title.

我以前从未使用过 JavaFX,所以我不确定在哪里可以找到这个模块.

I never used JavaFX before so I'm unsure of where to locate this module.

推荐答案

TL;DR:

确保将 JavaFX 解析为命名模块.

Make sure JavaFX is resolved as named modules.

  • 非模块化应用程序:

  • Non-modular application:

java --module-path <path-to-fx> --add-modules <fx-modules> ...

  • 模块化应用:

  • Modular application:

    java --module-path <path> --module <main-module>/<main-class> [args...]
    

    其中 包括您的模块以及 JavaFX.

    Where <path> includes your module as well as JavaFX.

    使用包含 JavaFX 的 JDK 发行版(有关更多信息,请参阅下面的答案).可能仍然需要使用 --add-modules.

    Use JDK distribution which includes JavaFX (see answer below for more information). May still need to use --add-modules.

    此警告与 Java 9 中引入的 Java 平台模块系统 (JPMS) 相关.如果您不熟悉模块,那么我建议您阅读 了解 Java 9 模块以获得简要概述.

    This warning is related to the Java Platform Module System (JPMS) introduced in Java 9. If you're not familiar with modules, then I recommend reading Understanding Java 9 Modules for a brief overview.

    JPMS 带来了模块路径,它现在与类路径一起存在.当从类路径加载类时,它们成为所谓的未命名模块的一部分.而模块路径上的类包含在模块中,因此被加载到"模块路径中.命名模块.命名模块可能是也可能不是自动,具体取决于它是否有 module-info 描述符.

    With JPMS came the module-path, which now exists alongside the class-path. When classes are loaded from the class-path they become a part of the so-called unnamed module. Whereas classes on the module-path are contained within modules, and are thus loaded "into" named modules. A named module may or may not be automatic, depending on if it has a module-info descriptor or not, respectively.

    JavaFX 仅支持作为命名模块加载.换句话说,JavaFX 只支持从模块路径加载,而不支持从类路径加载.从版本 9 开始,当框架模块化时,这一直是隐含的.但是现在,从版本 16 开始,如果 JavaFX 检测到它是从类路径加载的(即在未命名模块中),则会发出警告.请参阅 JDK-8256362.

    JavaFX only supports being loaded as named modules. In other words, JavaFX only supports being loaded from the module-path, not the class-path. This has been implicitly true since version 9, back when the framework was modularized. But now, as of version 16, a warning is emitted if JavaFX detects it was loaded from the class-path (i.e. is in the unnamed module). See JDK-8256362.

    解决方案是确保从模块路径加载 JavaFX 并解析为命名模块.注意 JavaFX 由七个模块组成,从其文档可以看出.

    The solution is to make sure JavaFX is loaded from the module-path and resolved as named modules. Note JavaFX is made up of seven modules, as can be seen by its documentation.

    您如何确保将 JavaFX 解析为命名模块可能取决于您的环境(例如,非模块化与模块化应用程序、外部 JavaFX SDK 等).下面的示例都使用命令行来显示如何设置所需的参数.但是,如果您使用的是 IDE(例如 NetBeans、IntelliJ、Eclipse)和/或构建工具(例如 Maven、Gradle)并且不确定在哪里设置这些参数,请查看 JavaFX 11+ 入门.

    How exactly you ensure JavaFX is resolved as named modules may depend on your environment (e.g. non-modular vs modular application, external JavaFX SDK, etc.). The examples below all use the command-line to show how to set the needed arguments. However, if you're using an IDE (e.g. NetBeans, IntelliJ, Eclipse) and/or a build tool (e.g. Maven, Gradle) and are unsure of where to set these arguments, then check out Getting Started with JavaFX 11+.

    请注意,Gradle 和 Maven 都有可以更轻松地使用 JavaFX 的插件(即它们为您处理所有配置).

    Note that both Gradle and Maven have plugins that make it easier to work with JavaFX (i.e. they handle all the configuration for you).

    如果您的代码是非模块化的,那么您就没有 module-info 描述符.这意味着将 JavaFX 添加到模块路径是不够的;您还必须强制 Java 解析 JavaFX 模块.这可以通过 --add-modules 参数来完成.

    If your code is non-modular then you do not have a module-info descriptor. This means adding JavaFX to the module-path is not enough; you also have to force Java to resolve the JavaFX modules. That can be done via the --add-modules argument.

    例如:

    java --module-path <path-to-fx> --add-modules javafx.controls ...
    

    注意我只在 --add-modules 参数中包含了 javafx.controls 模块.这是因为它需要 javafx.basejavafx.graphics 模块,这意味着它们将被隐式拉入.

    Notice I only include the javafx.controls module in the --add-modules argument. This is because it requires the javafx.base and javafx.graphics modules, which means they will be implicitly pulled in.

    如果您需要其他模块,那么您还需要将它们包含在 --add-modules 参数中,并用逗号分隔.

    If you need other modules then you need to include them in the --add-modules argument as well, separated by a comma.

    另外,请注意,在这种情况下,您的代码和其他非模块化依赖项可以放在类路径上.重要的部分是 JavaFX 是从模块路径加载的.

    Also, note it's okay, in this case, to have your code and other non-modular dependencies on the class-path. The important part is that JavaFX is loaded from the module-path.

    如果您的代码是模块化的,那么您有一个 module-info 描述符.该描述符将具有必要的 requires 指令.在这种情况下,您不再需要使用 --add-modules,但您需要确保通过 --module 将您的应用程序作为模块启动.

    If your code is modular then you will have a module-info descriptor. This descriptor will have the necessary requires directives. In this case, you no longer need to use --add-modules, but you do need to make sure to launch your application as a module via --module.

    例如:

    module app {
      // transitively requires javafx.base and javafx.graphics
      requires javafx.controls;
    
      // export javafx.application.Application implementation's package
      // to at least javafx.graphics
      exports com.example.app to javafx.graphics;
    }
    

    java --module-path <path> --module app/com.example.app.Main [args...]
    

    请注意,您不仅需要将 JavaFX 放在模块路径上,还需要将您自己的模块放在一起.

    Note for this you need to not only put JavaFX on the module-path, but also your own module.

    从 Java 11 开始,Oracle 提供的 JDK 中不再包含 JavaFX.但 Oracle 并不是基于 OpenJDK 的 Java 的唯一供应商.有一些供应商提供包含 JavaFX 的 JDK 发行版.其中至少有两个是:

    Since Java 11, JavaFX is no longer included in the JDK provided by Oracle. But Oracle is not the only vendor for Java based on OpenJDK. There are vendors out there that provide JDK distributions which include JavaFX. At least two of them are:

    • BellSoft Liberica JDK (make sure to choose the "Full JDK" option).
    • Azul Zulu JDK (make sure to choose the "JDK FX" package).

    当 JavaFX 包含在 JDK 中时,它现在与所有其他 Java 模块(例如 java.base)一样是运行时映像的一部分.这意味着它将自动加载为命名模块,您不再需要手动将 JavaFX 放在模块路径上.但是,如果您的应用程序是非模块化的,那么您可能仍然需要使用 --add-modules(不确定).

    When JavaFX is included in the JDK, it's now part of the run-time image like all the other Java modules (e.g. java.base). This means it will automatically be loaded as named modules and you no longer have to manually put JavaFX on the module-path. However, if your application is non-modular then you may still need to use --add-modules (not sure).

    当您要部署 JavaFX 应用程序时,在运行时映像中包含 JavaFX 可能是最简单的方法.您可以使用 jlink/jpackage 工具执行此操作.这可以通过包含 JavaFX 的 JDK 或外部 JavaFX SDK 来完成.但是,如果您使用后者,请确保在制作自定义运行时映像时使用 JMOD 文件(或使用来自 Maven Central 的 JavaFX JAR,它嵌入了所需的本机代码).

    When you go to deploy a JavaFX application, including JavaFX in the run-time image is likely the easiest approach. You can do this with the jlink / jpackage tools. And this can be done with either a JDK that includes JavaFX or an external JavaFX SDK. However, if you use the latter then make sure to use the JMOD files when making the custom run-time image (or use the JavaFX JARs from Maven Central, which embed the needed native code).

    如果您的代码是非模块化的,那么您将创建一个包含 JavaFX(以及您的应用程序所需的所有其他非自动命名模块)的自定义运行时映像,然后配置 jpackage 将您的代码(以及所有非模块化依赖项)放在类路径上.

    If your code is non-modular, then you'd create a custom run-time image that includes JavaFX (and all the other non-automatic named modules needed by your application), and then configure jpackage to place your code (and all non-modular dependencies) on the class-path.

    据我所知,如果从类路径加载 JavaFX,当前不会破坏任何内容.这意味着另一种选择,至少目前,是忽略警告.但是,我建议您至少在模块路径中放置 JavaFX,前提是您可以轻松完成此操作.

    As far as I can tell, nothing currently breaks if JavaFX is loaded from the class-path. This means another option, at least for now, is to just ignore the warning. However, I recommend putting at least JavaFX on the module-path if you can do so without too much trouble.

    这篇关于JavaFX 警告:不支持的 JavaFX 配置:类是从“未命名模块@..."加载的的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

  • 查看全文
    登录 关闭
    扫码关注1秒登录
    发送“验证码”获取 | 15天全站免登陆