在 JDK 11 上运行 javafx 样本,在模块路径上运行 OpenJFX 11 JMODS

2022-09-02 20:52:10

我已经从OpenJFX项目下载了JavaFX Jmod文件,并将它们放在目录中。我正在使用OpenJDK 11,它没有JavaFX jmod,即它没有JavaFX发行版。G:\openjfx\javafx-jmods-11JAVA_HOME/jmods

模块信息文件:

module gui{
    requires javafx.graphics;
    requires javafx.controls;

    exports com.test;
}

我用以下内容编译:

javac -p G:\openjfx\javafx-jmods-11 -d mods --module-source-path src 
    src\gui\com\test\*.java src\gui\module-info.java

编译成功。但是我无法使用以下命令运行编译的代码:

java -p G:\openjfx\javafx-jmods-11;mods -m gui/com.test.CreateGuiDemo

但是我得到以下错误:

Error occurred during initialization of boot layer
java.lang.module.FindException: Module javafx.graphics not found, required by gui

答案 1

我相信对于您面临的错误有一个解释:jmods不能在运行时使用

这里对此进行了解释:http://openjdk.java.net/jeps/261#Packaging:-JMOD-files

JMOD 文件可以在编译时和链接时使用,但不能在运行时使用。为了在运行时支持它们,通常需要我们准备好动态提取和链接本机代码库。

这个答案值得称赞。

所以我做了一些简单的模块:hellofx

module hellofx {
    requires javafx.controls;

    exports hellofx;
}

从这里使用示例,并从此处下载适用于我的平台的JavaFX 11的jmods我还从同一位置下载了JavaFX 11 SDK(jars)。HelloFX

编译时

在编译时,我们可以用jmods做:

javac -p /path-to/javafx-jmods-11/ -d mods/hellofx $(find src/hellofx -name "*.java")

或使用 SDK:

javac -p /path-to/javafx-sdk-11/lib -d mods/hellofx $(find src/hellofx -name "*.java")    

在这两种情况下,结果完全相同,正如预期的那样:编译时不需要本机库。

运行时间

现在我们要运行我们的小模块。

使用 jmods,如 OP 所述,运行:

java -p /path-to/javafx-jmods-11/:mods -m hellofx/hellofx.HelloFX   

失败,出现:

Error occurred during initialization of boot layer
  java.lang.module.FindException: Module javafx.controls not found, required by hellofx

但是使用SDK,工作原理:

java -p /path-to/javafx-sdk-11/lib/:mods -m hellofx/hellofx.HelloFX

链接时间

正如 JEP-261 所述,jmods 在链接时也可以工作,因此我们可以在编译时间和运行时之间使用该工具。jlink

可以使用 jlink 工具将一组模块及其依赖项组装和优化到自定义运行时映像中。(来源)

所以让我们做:

jlink -p /path-to/javafx-jmods-11/:mods --add-modules=hellofx --output links

这将生成一个90.7 MB的文件夹(在我的Mac上)。请注意,该文件夹包含 Java 11 和 JavaFX 11 中所有必需的本机库,以及一个名为 的 70.5 MB 文件。libmodules

运行时 (2)

我们终于可以做到:

links/bin/java -m hellofx/hellofx.HelloFX

这将起作用。

总之,如果我们只想使用jmods来编译和运行我们的模块,我们需要给一个额外的步骤。否则,对于运行时,我们将需要 JavaFX SDK。jlink


答案 2

如果未自动添加,请尝试在 pom.xml中使用此设置。请务必更改“!!您的主类名在这里!!“ 朝向代码底部,使用 main 方法将类的名称!如果我的类是示例.java我只想放在那里示例。

 <dependencies>
    <dependency>
        <groupId>org.openjfx</groupId>
        <artifactId>javafx-controls</artifactId>
        <version>11.0.2</version>
    </dependency>
    <dependency>
        <groupId>org.openjfx</groupId>
        <artifactId>javafx-fxml</artifactId>
        <version>11.0.2</version>
    </dependency>
</dependencies>
<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-compiler-plugin</artifactId>
            <version>3.8.0</version>
            <configuration>
                <release>11</release>
            </configuration>
        </plugin>
        <plugin>
            <groupId>org.codehaus.mojo</groupId>
            <artifactId>exec-maven-plugin</artifactId>
            <version>1.6.0</version>
            <executions>
                <execution>
                    <goals>
                        <goal>java</goal>
                    </goals>
                </execution>
            </executions>
            <configuration>
                <mainClass>!!YOUR MAIN CLASSNAME HERE!!</mainClass>
            </configuration>
        </plugin>
    </plugins>
</build>

JavaFX 不会自动添加为 Java 11 的依赖项。这就是我们需要手动添加的原因。


推荐