简体   繁体   English

主方法不在模块内运行

[英]Main method doesn't run inside a module

Do I need to run my main method inside a module or outside? 我是否需要在模块内或外部运行main方法?

I am new in using the modular system of Java. 我是使用Java模块化系统的新手。 I am trying create a simple program with JavaFX in Java 10, since it is the last version of Java that supports JavaFX. 我正在尝试使用Java 10中的JavaFX创建一个简单的程序,因为它是支持JavaFX的Java的最后一个版本。

I imported the necessary dependencies on my module-info.java for JavaFX which shows just a simple window. 我在我的module-info.java为JavaFX导入了必要的依赖项, module-info.java显示了一个简单的窗口。

sample.fxml code: sample.fxml代码:

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

When I build my code it says: 当我构建我的代码时,它说:

Warning:(4, 27) java: module not found: com.main

When I try to run my code I get: 当我尝试运行我的代码时,我得到:

Exception in Application constructor Exception in thread "main" java.lang.reflect.InvocationTargetException
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.base/java.lang.reflect.Method.invoke(Method.java:564)
    at java.base/sun.launcher.LauncherHelper$FXHelper.main(LauncherHelper.java:941)

Can anyone give me advice for this, or somehow a real world application advice about creating projects with the modular system. 任何人都可以为此提供建议,或者以某种方式提供有关使用模块化系统创建项目的实际应用建议。

I have attached a pair of screenshots below. 我在下面附上了一对截图。

Build Warning : 建立警告:

在此输入图像描述

Runtime Failure : 运行时失败:

在此输入图像描述

The possible suspect here is that you're using com.main as a module name within the module-info.java which the IDE complains to have not found in the project. 这里的犯罪嫌疑人可能是你使用com.main作为内的模块名称module-info.java该IDE会在项目还没有找到。

I would guess, this could be possibly be resolved using com.gui as the module name in the declaration. 我猜,这可能是使用com.gui作为声明中的模块名称来解决的。

The module system adds stronger encapsulation. 模块系统增加了更强的封装。 In other words, it is no longer the case that all classes are reflectively accessible to every other class. 换句话说,不再是所有类都可以被其他所有类反射访问。

When launching JavaFX the usual way, an instance of your Application subclass is instantiated for you. 以通常的方式启动JavaFX时,将为您实例化Application子类的实例。 This is done via reflection which means the module responsible for instantiating the subclass ( javafx.graphics ) must have the reflective access necessary to instantiate a public class with a public, no-arg constructor. 这是通过反射完成的,这意味着负责实例javafx.graphics类( javafx.graphics )的模块必须具有必要的反射访问权限,以使用public,no-arg构造函数实例化公共类。 To grant this access, the module containing the Application subclass must exports the appropriate package to at least javafx.graphics . 要授予此访问权限,包含Application子类的模块必须将相应的包exports至少 javafx.graphics

This is described in the documentation of Application : 这在Application 的文档中描述:

... ...

The Application subclass must be declared public and must have a public no-argument constructor. Application子类必须声明为public,并且必须具有公共无参数构造函数。

... ...

Deploying an Application as a Module 将应用程序部署为模块

If the Application subclass is in a named module then that class must be accessible to the javafx.graphics module. 如果Application子类位于命名模块中,那么javafx.graphics模块必须可以访问javafx.graphics Otherwise, an exception will be thrown when the application is launched. 否则,启动应用程序时将抛出异常。 This means that in addition to the class itself being declared public, the module must export (or open) the containing package to at least the javafx.graphics module. 这意味着除了类本身被声明为public之外,模块必须将包含的包导出(或打开)到至少javafx.graphics模块。

For example, if com.foo.MyApplication is in the foo.app module, the module-info.java might look like this: 例如,如果com.foo.MyApplicationfoo.app模块中,则module-info.java可能如下所示:

 module foo.app { exports com.foo to javafx.graphics; } 

You also seem to be using FXML. 你似乎也在使用FXML。 If necessary, you must make sure the appropriate packages are reflectively accessible to javafx.fxml (eg the controller class). 如有必要,您必须确保javafx.fxml (例如控制器类)可以反射访问相应的包。 This is documented in Introduction to FXML : 这在FXML简介中有记录:

Deploying an Application as a Module 将应用程序部署为模块

If FXMLLoader is used to load types in a named module, the application must ensure that all types that are referenced in the FXML files, including the controller class and any custom Node classes, are reflectively accessible to the javafx.fxml module. 如果FXMLLoader用于在命名模块中加载类型,则应用程序必须确保javafx.fxml模块可以反射地访问FXML文件中引用的所有类型,包括控制器类和任何自定义Node类。 A type is reflectively accessible if the module opens the containing package to at least the javafx.fxml module. 如果模块opens包含至少javafx.fxml模块的包,则可以反射访问类型。

For example, if com.foo.MyController is in the foo.app module, the module-info.java might look like this: 例如,如果com.foo.MyControllerfoo.app模块中,则module-info.java可能如下所示:

 module foo.app { opens com.foo to javafx.fxml; } 

I fixed this problem by making sure that: 我通过确保:

the modules that requires javafx dependencies also exports itself cause some javafx packages or modules needs the modules that requires it. 需要javafx依赖项的模块也会自行导出,因为某些javafx软件包或模块需要需要它的模块。

ex. 恩。 javafx.graphics javafx.graphics

Also make sure that the fxml resource is correct. 还要确保fxml资源正确。

1.) Correction on fxml resource: 1.)对fxml资源的更正:

在此输入图像描述

2.) Exporting the module that requires javafx dependencies: 2.)导出需要javafx依赖项的模块:

Error: (Read) 错误:(阅读)

Caused by: java.lang.IllegalAccessException: class com.sun.javafx.application.LauncherImpl (in module javafx.graphics) cannot access class com.gui.GUI (in module com.gui) because module com.gui does not export com.gui to module javafx.graphics
    at java.base/jdk.internal.reflect.Reflection.newIllegalAccessException(Reflection.java:360)
    at java.base/java.lang.reflect.AccessibleObject.checkAccess(AccessibleObject.java:589)
    at java.base/java.lang.reflect.Constructor.newInstance(Constructor.java:479)
    at javafx.graphics/com.sun.javafx.application.LauncherImpl.lambda$launchApplication1$8(LauncherImpl.java:875)
    at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runAndWait$11(PlatformImpl.java:449)
    at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runLater$9(PlatformImpl.java:418)
    at java.base/java.security.AccessController.doPrivileged(Native Method)
    at javafx.graphics/com.sun.javafx.application.PlatformImpl.lambda$runLater$10(PlatformImpl.java:417)
    at javafx.graphics/com.sun.glass.ui.InvokeLaterDispatcher$Future.run(InvokeLaterDispatcher.java:96)
    at javafx.graphics/com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
    at javafx.graphics/com.sun.glass.ui.win.WinApplication.lambda$runLoop$3(WinApplication.java:175)

Solution : module-info.java 解决方案: module-info.java

module com.gui {
    requires javafx.graphics;
    requires javafx.fxml;
    exports com.gui;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM