带有动画的JavaFX最小化和最大化未修饰的舞台

问题描述 投票:5回答:1

我在此问题中使用了可接受的答案:JavaFX Minimizing Undecorated Stage以适当地最小化我的应用。

但是,不幸的是,默认的Windows最小化和最大化动画根本没有显示(窗口只是显示和消失)。

我知道有可能使动画显示在未修饰的窗口中,因为我有一个具有这种行为的应用程序(PotPlayer)。

如何使动画与JNA一起显示?

EDIT:这是一个有效的Kotlin代码段,用于适当地最小化JavaFX窗口,并增加了赏金。

fun makeMinimizable(stage: Stage) {
         val user32 = User32.INSTANCE
         val hWnd = user32.FindWindow(null, stage.title)
         val oldStyle = user32.GetWindowLong(hWnd, WinUser.GWL_STYLE)
         val newStyle = oldStyle or 0x00020000 // WS_MINIMIZEBOX
         user32.SetWindowLong(hWnd, WinUser.GWL_STYLE, newStyle)
    }
javafx jna
1个回答
0
投票

根据对Windows动画的进一步研究,似乎可以一起破解一个解决方案。它似乎更多是操作系统问题,而不仅仅是JavaFX。

通过在start()中进行修改,我可以使初始窗口保持未修饰的状态,同时将其最小化并使用动画:

    int newStyle = oldStyle | 0x00020000 | 0x00C00000;

但是,最小化并重新打开后,Windows边框显得奇怪。

然后,我试图在图标化时使用ChangeListener交换Windows样式。

stage.iconifiedProperty().addListener(new ChangeListener<Boolean>() {

        @Override
        public void changed(ObservableValue<? extends Boolean> ov, Boolean t, Boolean t1) {
            if (t1.booleanValue() == true) {
                int newStyle = oldStyle | 0x00020000 | 0x00C00000;
                user32.SetWindowLong(hwnd, GWL_STYLE, newStyle);
            } else if (t1.booleanValue() == false) {
                int newStyle = oldStyle | 0x00020000;
                user32.SetWindowLong(hwnd, GWL_STYLE, newStyle);
            }
        }
    });

这成功地使窗口最小化动画以始终正常工作,同时使(可见)舞台无边界。

[一旦我找到了重新申请的最佳方法,看来我可以使最小化动画正常工作:

    int newStyle = oldStyle | 0x00020000 | 0x00C00000;
    user32.SetWindowLong(hwnd, GWL_STYLE, newStyle);

就在图标化舞台之前,并且边框对用户不可见。一旦实现,它可能与下面第一个链接中的C#解决方案类似。基本上,以上ChangeListener的作用相反。

我认为我们需要另一个线程在后台侦听以完成此解决方案,等待图标化事件发生。我认为在触发事件时应该是stage.isIconified()== false,然后我们在后台线程中执行必要的任务来设置上述代码。然后,(最小化工作时)changeListener会将其重置回没有动画的非框架窗口,当取消最小化时,直到将其再次最小化。

[有一个小错误,第一个未缩小显示我的舞台的底部被剪切并复制了一点,但是在后续操作后消失了。我们可能需要尝试将第二个十六进制更改为触发动画的其他内容,并在ChangeListener和其他线程中设置所有内容。

我计划很快在自己的fx程序中完成此操作。我仍然是一名学生,所以我对多线程和服务没有太多的经验,但是我对如何进行处理有一个很好的主意,只需花几个小时就可以破解。

让我知道您在此期间是否取得任何进展!这是一个很好的起点。尚无人用Java解决此问题。我正在阅读有关Steam等无边界程序已做到的一些讨论,但我认为没有人能完全弄清楚他们是如何实现的,我怀疑这是通过下面的C#hack实现的。但是,对于我们的目的而言已经足够了。

与解决无边界/未经修饰的动画有关的链接:

https://stackoverflow.com/a/31489766/7234125

^我们需要实现此答案,选项1,从C#到Java

https://exceptionshub.com/borderless-window-using-areo-snap-shadow-minimize-animation-and-shake.html

http://pinvoke.net/default.aspx/Constants/Window%20styles.html

© www.soinside.com 2019 - 2024. All rights reserved.