【问题标题】:JavaFX stylesheets inside OSGi bundleOSGi 包中的 JavaFX 样式表
【发布时间】:2013-11-28 20:03:03
【问题描述】:

我已将“styles.css”放在我的包的根目录中,现在试图弄清楚如何在代码中链接它。问题是 @.getStylesheets().add(_) 需要一个字符串而不是 URL,所以我知道的所有方法都在这里失败:

第 1 次:

scene.getStylesheets().add("styles.css");

Nov 15, 2013 2:04:47 PM com.sun.javafx.css.StyleManager loadStylesheetUnPrivileged
WARNING: Resource "styles.css" not found.

采取 2:

scene.getStylesheets().add(this.getClass().getResource("styles.css").toExternalForm());

NullPointerException

采取 3:

scene.getStylesheets().add(this.getClass().getClassLoader().getResource("styles.css").toExternalForm());

Nov 15, 2013 2:27:31 PM com.sun.javafx.css.StyleManager loadStylesheetUnPrivileged
INFO: Could not load stylesheet: bundle://5.0:1/styles.css

采取 4:

scene.getStylesheets().add(myBundle.getEntry("styles.css").toExternalForm());

Nov 15, 2013 1:31:35 PM com.sun.javafx.css.StyleManager loadStylesheetUnPrivileged
INFO: Could not load stylesheet: bundle://5.0:0/styles.css

我正在使用 Felix-4.2.1Java-8 (build 1.8.0-ea-b115)JavaFX-8 (8.0. 0-ea-b115).

【问题讨论】:

    标签: java javafx osgi javafx-8 java-8


    【解决方案1】:

    我最近遇到了与该问题的原始发布者相同的错误/麻烦,并且我设法解决了它,而无需对 css/fxml 进行任何更改或将其提取到临时文件中。因为网上没有找到好的答案,所以发在这里:

    就我而言,设置是:

    捆绑0:

    • someview.fxml 具有对 css 文件的相对路径引用
    • somestyle.css 带有对图像的相对路径引用
    • someimage.png
    • Resourceloader.java(从 css 和 fxml 文件返回 URL 对象)

    捆绑1:

    • 使用来自 bundle0 的 fxml 加载器加载 fxml 的基本 javafx 文件。

    问题:

    所有 css 和 css 引用的图像似乎都被 fxml 忽略了,即使我在 fxml 加载器上设置了类加载器。仅当我对 css 和 css 中引用的图像使用绝对文件路径时,它才有效。这不是我想要的。

    解决办法:

    JavaFX 中有 2 个错误/设计问题阻止此设置与 OSGi 一起使用。

    • 从 fxml 加载 css
    • 引用 CSS 中的图像

    要解决第一个问题,您必须通过将系统属性 binary.css 设置为 false 来禁用 javafx 中的二进制 css 文件。 javafx 中有一个错误(可能已经修复?),即使您说 css,javafx 也试图变得聪明并尝试找到 bss 文件。它翻转是因为 OSGi 资源 URL 有一个“bundle://”模式,它不需要模式。解决方案:

    • -Dbinary.css=false

    要解决第二个问题,您必须将线程上下文类加载器设置为css图像所在的bundle的类加载器,然后恢复线程上下文类加载器。诀窍是每次 css 由 JavaFX 解释时都这样做,这并不总是您期望的......

    ClassLoader tccl = Thread.currentThread().getContextClassLoader();
            try {
                final ClassLoader resourcesClassLoader = Resourceloader.class.getClassLoader();
            //needed for css
            Thread.currentThread().setContextClassLoader(resourcesClassLoader);
            this.primaryStage.show();
        } finally {
            Thread.currentThread().setContextClassLoader(tccl);
        }
    

    不幸的是,这是我能想到的最佳解决方案。 JavaFX 并没有考虑到类加载器或依赖注入,即使几乎每个企业应用程序都以某种形式使用这些功能。 :(

    //编辑 看起来你不需要设置线程上下文类加载器来访问来自 css 的图像!

    【讨论】:

      【解决方案2】:

      这里解释了这不起作用的原因:javafx jira RT-14177。 由于您不能使用资源的“ExternalForm”,因此我通过直接读取输入流将其复制到临时文件中。

              InputStream inputStream = MainApp.class.getResourceAsStream("/styles/styles.css");
              File tempStyleSheetDest = File.createTempFile("javafx_stylesheet", "");
              tempStyleSheetDest.deleteOnExit();
              Files.copy(inputStream, tempStyleSheetDest.toPath(), StandardCopyOption.REPLACE_EXISTING);
              scene.getStylesheets().add(tempStyleSheetDest.toURI().toString());
      

      我真的希望这对你有所帮助。

      乔纳森

      【讨论】:

        【解决方案3】:
        • 确保您使用的类加载器可以访问包含 css 文件的包
        • 如果您使用的是相对路径,请确保 css 位于相对于该类的包的位置

        这是我如何在Drombler FX (Drombler FX is a modular Rich Client Platform for JavaFX based on OSGi and Maven (POM-first)) 中加载 css 文件的示例:

        http://sourceforge.net/p/drombler/drombler-fx/ci/default/tree/drombler-fx-core-docking/src/main/java/org/drombler/fx/core/docking/impl/skin/Stylesheets.java

        这里:Stylesheets 类与 css 文件在同一个包中。

        【讨论】:

          【解决方案4】:

          getClass().getClassloader().getResource().toExternalForm()?

          【讨论】:

          • 与基于捆绑的变体相同的麻烦,但感谢您的尝试 - 我已将其包含在发布中。
          • 因为它在 Equinox 上对我有效,而对于 @puce,你的设置有问题吗?是否有可能您的 IDE 没有在类路径上复制 CSS 文件(例如,在 eclipse 中它必须是 bin 文件夹的一部分)
          • 我检查了 jar,一切正常。它实际上看到了 css 文件,但无法加载它(“信息:无法加载样式表”与“警告:找不到资源“styles.css”。”)。也许问题出在最后的 felix、javafx 或 java 中。目前,我已经切换到嵌入式 felix(处理包外的 javafx 部分),一切都很好。
          猜你喜欢
          • 2012-10-25
          • 2017-06-18
          • 2017-05-17
          • 2016-01-31
          • 2015-04-28
          • 2018-07-11
          • 2013-11-30
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多