【问题标题】:Designing a splash screen (java)设计启动画面 (java)
【发布时间】:2012-04-17 08:35:04
【问题描述】:

我想设计一个可以用进度条显示当前加载过程的闪屏, 很像 netbeans 启动屏幕,因为它显示

loading... modules, done!.... loading modules and so on 

加载完成后,主应用程序出现。

我已经阅读了许多仅与创建初始屏幕相关的文章,但没有一篇涉及如何在初始屏幕上显示不同后台任务的进度。

我怎样才能做到这一点?

我可以使用 javafx 2 作为启动屏幕,而应用程序的其余部分是使用 java 编写的吗

解决了!

我终于设法让它工作了。 我的错误是我正在更新任务线程中的 GUI 内容,所以我的任务线程被阻止并且无法在 GUI 更新指令之后执行下一个指令。现在我在任务完成后转移了那些更新 GUI 指令,及其工作...... 感谢 Jewelsea 的正确路径。

【问题讨论】:

  • 我可以说不要这样做吗?我不知道有谁真正喜欢启动画面——当软件把它推到我脸上时,我讨厌它,只是在后台加载并在你拥有它时显示窗口。不过可能只是我。
  • 在我看来,当您的软件/应用程序需要一些时间来加载(例如建立数据库连接、获取数据)时,启动画面是很好的,因此用户实际上可以看到那里有一些处理。
  • 这肯定是桌面环境的问题吗?例如,KDE 在光标旁边显示弹跳应用程序图标,以向用户提供应用程序正在启动的反馈。当然,最好的选择是让它成为用户的偏好——这样你就可以让每个人都开心。
  • 没错,我的应用程序 (javafx+java) 大约需要 10 秒才能加载...
  • 知道 netbeans 是如何做到这一点的吗?

标签: java swing splash-screen javafx-2


【解决方案1】:

我之前为独立的 JavaFX 2.0 应用程序创建了一个 splash page sample

我更新了示例,以演示通过启动页面上的进度条和进度文本监控加载进度。

要调整代码以监控应用程序的初始化进度,而不是将ProgressBar 绑定到WebEngine 的loadWorker.workDone 属性,创建一个JavaFX Task 执行昂贵的初始化工作,并监控@ 的进度987654329@ 通过任务的progressPropertymessageProperty

这里是一个指向 splash based sample 的链接,该链接基于上一段中概述的任务方法。

对于 WebStart 或浏览器嵌入式 JavaFX 应用程序,请按照 assylias 的建议使用 preloader

【讨论】:

  • 所以你的意思是说我必须为每个后台进程创建不同的任务并在初始屏幕上显示这些任务进度属性?
  • 我尝试实现它,假设 showProcess 是我的启动画面,showProcess.progressBar.progressProperty().bind(task.workDoneProperty().divide(100)); showProcess.showVisible(true);任务运行();现在当我运行此代码任务时不会执行。我错过了什么吗?
  • 更新了链接的答案以另外链接到基于任务的解决方案。
  • 非常感谢jewelsea,我终于让它工作了。 :) 我的错误是我正在更新任务线程中的 GUI 内容,所以我的任务线程被阻止并且在 GUI 更新指令之后无法执行下一个指令(在我看来)。现在我在任务完成后转移了那些更新 GUI 指令,它的工作......
  • 嗨,jewelsea。你的飞溅样本效果很好。在商业应用程序中采用代码是否有任何限制?谢谢。
【解决方案2】:

如果您使用 进行部署,icon element 可以引用各种图像中的任何一个。在下载过程中,进度指示由jnlp 客户端处理。优势在于很早就介入用户体验。

稍后,SwingWorker 可以在后台加载图像,如here 所示。 worker的progress()方法可以通过PropertyChangeListener驱动JProgressBar,如图here

【讨论】:

    【解决方案3】:

    使用preloader 来显示应用程序初始化的进度似乎正是您想要的。

    【讨论】:

    • 预加载器适用于 WebStart 和浏览器嵌入式应用程序,但(从 JavaFX 2.0 开始)不针对独立应用程序。
    • 似乎对于 JavaFX 2.1+,预加载器也可以用于独立应用程序的初始化 - 但我还没有尝试过。
    【解决方案4】:

    查看Swing splash-screen tutorial,其中包含一个示例,其中在初始屏幕上更新了进度条。您可以轻松地调整示例以更新一些文本。

    【讨论】:

    • 除非您不能使用 Swing/AWT 组件,例如 JProgressBar,因为它会使启动画面消失。你必须把它画在SplashScreen.createGraphics()...
    【解决方案5】:

    您还可以使用 java 创建启动画面,

    但如果您想减少代码并做更多的事情而不是使用 JavaFx 闪屏组件。

    【讨论】:

    • 我试过了,但我也想显示后台进程的进度,
    【解决方案6】:

    为了完整起见,如果您想显示进度条。引用SplashScreen javadoc

    启动画面窗口会在第一次出现时自动关闭 窗口由 Swing/AWT 显示。

    这意味着它不能使用标准的 AWT/Swing 组件(例如JProgressBar),而只能通过Graphics2D 方法(例如drawText()fillRect()、...)进行绘制。

    所以你必须在一个单独的类中模拟一个进度条(代码作为一个非常粗略的演示给出。你应该检查SplashScreen.isVisible()):

    public class SplashProgressBar {
    
        SplashScreen splash;
        Graphics2D g;
        int x, y, w, h; // Drawing position in splash screen
    
        int val, max; // Progress bar value
        String text; // Text to display
    
        public SplashProgressBar(SplashScreen splash, int x, int y, int w, int h) {
            this.splash = splash;
            g = splash.createGraphics();
            this.x = x;
            // this.y = y; etc
            this.val = 0;
            this.max = 100;
        }
    
        public void setMaximum(int n) {
            max = n;
            update();
        }
    
        public void setValue(int n) {
            val = n;
            update();
        }
    
        public void setString(String text) {
            this.text = text;
            update();
        }
    
        public void update() {
            g.setColor(Color.WHITE);
            g.fillRect(x, y, w, h);
            g.setColor(Color.DARK_GRAY);
            g.drawRect(x, y, w, h);
            g.setColor(Color.ORANGE);
            g.fill3DRect(x, y, w * val / max, h, true);
            if (text != null) {
                g.setColor(Color.BLACK);
                g.drawString(text, x + (w - g.getFontMetrics().stringWidth(text)) / 2.0f, y + 8 - 2); // Use TextLayout to get precise text dimensions...
            }
            splash.update();
        }
    }
    

    然后:

    // Drawn a scroll bar at (10;100) x (300x15) on the splash screen image (we know its size and where it would fit)
    SplashProgressBar spb = new SplashProgressBar(SplashScreen.getSplashScreen(), 10, 100, 300, 15);
    spb.setMaximum(processing.size());
    for (int i = 0; i < processing.size(); i++) {
        spb.setValue(i);
        spb.setString("Processing #"+(i+1));
        // Do the processing...
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-01-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多