19

我现在正在开发一个简单的QML应用程序,例如,我注意到调整窗口大小和移动QML窗口与窗口相比会产生难看的闪烁QtWidgets

所以我创建了 2 个测试应用程序来显示差异:

QWidgets:

在此处输入图像描述

QML:

在此处输入图像描述

如您所见,应用程序的版本在干净QML时闪烁得很丑。QtWidgets现在,当您的 UI 变得越来越复杂时,这变得非常难看。

你有这方面的知识吗?这是一个错误吗?此问题是否有任何修复/解决方法?

4

4 回答 4

9

你可以试试这个:

int main(int argc, char* argv[]) {
QCoreApplication::setAttribute(Qt::AA_UseOpenGLES);
or
QCoreApplication::setAttribute(Qt::AA_UseSoftwareOpenGL);

第一个选项使用 OpenGl2DirecX 角度库(如 Google Chrome)

第二个是通过软件使用 OpenGL 仿真……小程序运行良好,并且与 Windows XP 等旧操作系统 100% 兼容。

注意:您可以尝试使用 Qt 5.7 和新的 Qtquick.Controls 2.0 ...性能更好... https://blog.qt.io/blog/2016/06/10/qt-quick-controls-2-0 -一个新的开始/

于 2016-10-04T15:00:14.190 回答
3

调整 QML 应用程序大小的问题在于更新带有过时几何图形的窗口。解决方法是同步更新和调整大小。

由于更新计时器可能会突然更新到渲染场景图,它可以随时更新窗口,因此会导致绘制具有过时几何图形的内容。 https://bugreports.qt.io/browse/QTBUG-46074

应该使用基本同步或扩展同步来同步调整大小和窗口更新。目前基本同步在 Qt 中使用和实现,但仍需要将窗口更新(来自计时器)与来自 Windows 管理器的调整大小事件同步。

但是,与往常一样,有一系列问题:

当窗口大小调整过快时会出现问题。由于应该一致地发送同步事件(来自 WM),因此下一个在上一个之后:

  1. <= _NET_WM_SYNC_REQUEST 是从 WM 发送的,现在大小正在改变。

  2. _NET_WM_SYNC_REQUEST 由应用程序接收和处理。

  3. <= 收到其他一些事件,例如新几何。

  4. .. 更新内容,swapBuffers。

  5. => 将 _NET_WM_SYNC_REQUEST_COUNTER 发送回 WM。

  6. <= _NET_WM_SYNC_REQUEST 从 WM 再次发送,大小正在变化。

  7. .. swapBuffers // 这是问题所在,更新是在窗口更改其几何形状时执行的。

  8. _NET_WM_SYNC_REQUEST 收到并再次处理。

因此,在发送 _NET_WM_SYNC_REQUEST 但尚未接收/处理之后出现 (7) swapBuffers 时,就会出现问题。

最后得出结论:

  • 窗口管理器发送_NET_WM_SYNC_REQUEST 后立即开始实际调整窗口大小。而不是当应用程序收到它时。此时窗口甚至可以在发送同步请求时更新,但尚未由应用程序处理。这将使用过时的几何图形绘制内容。
  • _NET_WM_FRAME_DRAWN 可以帮助在调整大小和更新之间进行同步,但也可能不被窗口管理器支持(并且猜测它不是)。

换句话说,无论是基本同步还是扩展同步都无济于事(至少没有 _NET_WM_FRAME_DRAWN),因为无法知道实际调整大小的时间。

扩展同步协议试图处理这个问题,但由于几何的实际更改是在没有与客户端同步的情况下完成的,正如我所看到的,没有 _NET_WM_FRAME_DRAWN 总是有机会用过时的几何更新窗口。

https://lists.freedesktop.org/archives/xcb/2019-February/011280.html

于 2019-06-27T09:08:11.683 回答
1

就我而言,我通过添加下一个标志解决了这个问题:

QQuickWindow::setSceneGraphBackend(QSGRendererInterface::Software);

但这会增加其他渲染问题。或不。

于 2017-10-22T14:44:55.833 回答
1

在 golang 配方/qt 这对我有帮助:

func main() {
    var format = gui.NewQSurfaceFormat()
    format.SetVersion(4, 5)
    format.SetProfile(gui.QSurfaceFormat__CoreProfile)
    format.SetRenderableType(gui.QSurfaceFormat__OpenGL)
    format.SetSwapInterval(0)
    format.SetDefaultFormat(format)
    os.Setenv("QT_SCALE_FACTOR", "1")
    ap := widgets.NewQApplication(len(os.Args), os.Args)
    ap.SetApplicationName("APP 1.1")

系统:Linux debian 10 gpu:Radeon 570

但动画更快,因为并非所有帧都被渲染......

于 2020-01-16T22:15:36.727 回答