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

使用Maven构建JavaFX可双击运行Jar包遇到的问题

问题解决:非模块化JavaFX应用Maven警告及双击Jar运行方案

一、解决Maven依赖警告

[WARNING] Failed to build parent project for org.openjfx:javafx-controls:jar:17.0.10 警告的核心原因是JavaFX依赖分平台(win/linux/mac)发布,未指定平台分类器时Maven无法拉取完整依赖包。

修复方案

在pom.xml中添加Maven配置文件,自动匹配当前操作系统的JavaFX依赖:

<properties>
    <!-- 新增默认分类器,可由profile自动覆盖 -->
    <javafx.classifier>win</javafx.classifier>
</properties>

<profiles>
    <profile>
        <id>windows</id>
        <activation>
            <os>
                <family>windows</family>
            </os>
        </activation>
        <properties>
            <javafx.classifier>win</javafx.classifier>
        </properties>
    </profile>
    <profile>
        <id>linux</id>
        <activation>
            <os>
                <family>linux</family>
            </os>
        </activation>
        <properties>
            <javafx.classifier>linux</javafx.classifier>
        </properties>
    </profile>
    <profile>
        <id>mac</id>
        <activation>
            <os>
                <family>mac</family>
            </os>
        </activation>
        <properties>
            <javafx.classifier>mac</javafx.classifier>
        </properties>
    </profile>
</profiles>

然后修改所有JavaFX依赖,添加分类器参数:

<dependency>
    <groupId>org.openjfx</groupId>
    <artifactId>javafx-controls</artifactId>
    <version>${javafx.version}</version>
    <classifier>${javafx.classifier}</classifier>
</dependency>
<dependency>
    <groupId>org.openjfx</groupId>
    <artifactId>javafx-fxml</artifactId>
    <version>${javafx.version}</version>
    <classifier>${javafx.classifier}</classifier>
</dependency>
<dependency>
    <groupId>org.openjfx</groupId>
    <artifactId>javafx-graphics</artifactId>
    <version>${javafx.version}</version>
    <classifier>${javafx.classifier}</classifier>
</dependency>

二、实现双击运行的Jar包

maven-assembly-plugin无法正确处理JavaFX的模块依赖,导致双击时JVM无法加载JavaFX核心类。推荐使用maven-shade-plugin替代,它能整合模块信息并生成可直接运行的Jar。

替换插件配置

移除原有的maven-assembly-plugin和maven-jar-plugin,添加以下配置:

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-shade-plugin</artifactId>
    <version>3.4.1</version>
    <executions>
        <execution>
            <phase>package</phase>
            <goals>
                <goal>shade</goal>
            </goals>
            <configuration>
                <shadedArtifactAttached>true</shadedArtifactAttached>
                <shadedClassifierName>all</shadedClassifierName>
                <transformers>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
                        <mainClass>${mainClass}</mainClass>
                        <manifestEntries>
                            <Automatic-Module-Name>com.BO</Automatic-Module-Name>
                        </manifestEntries>
                    </transformer>
                    <transformer implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer"/>
                </transformers>
                <filters>
                    <filter>
                        <artifact>*:*</artifact>
                        <excludes>
                            <exclude>META-INF/*.SF</exclude>
                            <exclude>META-INF/*.DSA</exclude>
                            <exclude>META-INF/*.RSA</exclude>
                        </excludes>
                    </filter>
                </filters>
            </configuration>
        </execution>
    </executions>
</plugin>

主类要求

确保你的主类main.Main符合以下任一条件:

  1. 直接继承javafx.application.Application并实现start()方法;
  2. 普通类的main方法中调用JavaFX启动器:
public class Main {
    public static void main(String[] args) {
        javafx.application.Application.launch(YourFXApplication.class, args);
    }
}

三、跨设备运行进阶方案(推荐)

如果需要在未安装JDK/JRE的设备上运行,使用javafx-maven-plugin的jlink目标生成自包含应用包,包含专属JRE和所有依赖:

<plugin>
    <groupId>org.openjfx</groupId>
    <artifactId>javafx-maven-plugin</artifactId>
    <version>0.0.8</version>
    <configuration>
        <mainClass>${mainClass}</mainClass>
        <jlinkImageName>BO-App</jlinkImageName>
        <jlinkZipName>BO-App-Zip</jlinkZipName>
        <launcher>BO-Launcher</launcher>
    </configuration>
    <executions>
        <execution>
            <id>jlink</id>
            <goals>
                <goal>jlink</goal>
            </goals>
        </execution>
    </executions>
</plugin>

执行mvn clean jlink后,target/BO-App目录会生成对应平台的可执行文件(Windows为.exe、Linux为.sh、Mac为.app),双击即可运行。

四、完整修改后的pom.xml

<groupId>com.BO</groupId>
<artifactId>BO</artifactId>
<version>1.0-SNAPSHOT</version>

<properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <junit.version>5.9.2</junit.version>
    <itext.version>8.0.5</itext.version>
    <javafx.version>17.0.10</javafx.version>
    <mainClass>main.Main</mainClass>
    <javafx.classifier>win</javafx.classifier>
</properties>

<profiles>
    <profile>
        <id>windows</id>
        <activation>
            <os>
                <family>windows</family>
            </os>
        </activation>
        <properties>
            <javafx.classifier>win</javafx.classifier>
        </properties>
    </profile>
    <profile>
        <id>linux</id>
        <activation>
            <os>
                <family>linux</family>
            </os>
        </activation>
        <properties>
            <javafx.classifier>linux</javafx.classifier>
        </properties>
    </profile>
    <profile>
        <id>mac</id>
        <activation>
            <os>
                <family>mac</family>
            </os>
        </activation>
        <properties>
            <javafx.classifier>mac</javafx.classifier>
        </properties>
    </profile>
</profiles>

<repositories>
    <repository>
        <id>maven-repo-itext</id>
        <url>https://repo.itextsupport.com/nexus/content/groups/public/</url>
    </repository>
    <repository>
        <id>openjfx</id>
        <url>https://openjfx.io/repo</url>
    </repository>
</repositories>

<dependencies>
    <dependency>
        <groupId>net.sourceforge.jtds</groupId>
        <artifactId>jtds</artifactId>
        <version>1.3.1</version>
    </dependency>
    <dependency>
        <groupId>com.microsoft.sqlserver</groupId>
        <artifactId>mssql-jdbc</artifactId>
        <version>8.4.1.jre8</version>
    </dependency>
    <dependency>
        <groupId>com.itextpdf</groupId>
        <artifactId>itextpdf</artifactId>
        <version>5.5.13.4</version>
    </dependency>
    <dependency>
        <groupId>org.apache.poi</groupId>
        <artifactId>poi</artifactId>
        <version>5.2.3</version>
    </dependency>
    <dependency>
        <groupId>org.apache.poi</groupId>
        <artifactId>poi-ooxml</artifactId>
        <version>5.2.3</version>
    </dependency>
    <dependency>
        <groupId>org.apache.poi</groupId>
        <artifactId>poi-ooxml-schemas</artifactId>
        <version>4.1.2</version>
    </dependency>
    <dependency>
        <groupId>org.apache.xmlbeans</groupId>
        <artifactId>xmlbeans</artifactId>
        <version>5.1.1</version>
    </dependency>
    <dependency>
        <groupId>com.itextpdf</groupId>
        <artifactId>kernel</artifactId>
        <version>8.0.5</version>
    </dependency>
    <dependency>
        <groupId>com.itextpdf</groupId>
        <artifactId>layout</artifactId>
        <version>8.0.5</version>
    </dependency>
    <dependency>
        <groupId>org.openjfx</groupId>
        <artifactId>javafx-controls</artifactId>
        <version>${javafx.version}</version>
        <classifier>${javafx.classifier}</classifier>
    </dependency>
    <dependency>
        <groupId>org.openjfx</groupId>
        <artifactId>javafx-fxml</artifactId>
        <version>${javafx.version}</version>
        <classifier>${javafx.classifier}</classifier>
    </dependency>
    <dependency>
        <groupId>org.openjfx</groupId>
        <artifactId>javafx-graphics</artifactId>
        <version>${javafx.version}</version>
        <classifier>${javafx.classifier}</classifier>
    </dependency>
    <dependency>
        <groupId>org.junit.jupiter</groupId>
        <artifactId>junit-jupiter-api</artifactId>
        <version>${junit.version}</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.junit.jupiter</groupId>
        <artifactId>junit-jupiter-engine</artifactId>
        <version>${junit.version}</version>
        <scope>test</scope>
    </dependency>
</dependencies>

<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-compiler-plugin</artifactId>
            <version>3.11.0</version>
            <configuration>
                <source>22</source>
                <target>22</target>
            </configuration>
        </plugin>
        <plugin>
            <groupId>org.openjfx</groupId>
            <artifactId>javafx-maven-plugin</artifactId>
            <version>0.0.8</version>
            <configuration>
                <mainClass>${mainClass}</mainClass>
                <jlinkImageName>BO-App</jlinkImageName>
                <jlinkZipName>BO-App-Zip</jlinkZipName>
                <launcher>BO-Launcher</launcher>
            </configuration>
            <executions>
                <execution>
                    <id>default-cli</id>
                    <goals>
                        <goal>run</goal>
                    </goals>
                </execution>
                <execution>
                    <id>jlink</id>
                    <goals>
                        <goal>jlink</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-shade-plugin</artifactId>
            <version>3.4.1</version>
            <executions>
                <execution>
                    <phase>package</phase>
                    <goals>
                        <goal>shade</goal>
                    </goals>
                    <configuration>
                        <shadedArtifactAttached>true</shadedArtifactAttached>
                        <shadedClassifierName>all</shadedClassifierName>
                        <transformers>
                            <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
                                <mainClass>${mainClass}</mainClass>
                                <manifestEntries>
                                    <Automatic-Module-Name>com.BO</Automatic-Module-Name>
                                </manifestEntries>
                            </transformer>
                            <transformer implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer"/>
                        </transformers>
                        <filters>
                            <filter>
                                <artifact>*:*</artifact>
                                <excludes>
                                    <exclude>META-INF/*.SF</exclude>
                                    <exclude>META-INF/*.DSA</exclude>
                                    <exclude>META-INF/*.RSA</exclude>
                                </excludes>
                            </filter>
                        </filters>
                    </configuration>
                </execution>
            </executions>
        </plugin>
    </plugins>
</build>

五、使用说明

  1. 执行mvn clean package,Maven自动匹配当前平台依赖,警告消失,target目录生成BO-1.0-SNAPSHOT-all.jar,双击即可运行;
  2. 执行mvn clean jlink,生成自包含应用包,可直接在对应平台分发运行,无需额外安装JDK。

内容的提问来源于stack exchange,提问作者David Carmona Arrabal

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.17 04:14:52