【问题标题】:Using QOpenGLWidget with QGraphicsView: viewport not updating?将 QOpenGLWidget 与 QGraphicsView 一起使用:视口未更新?
【发布时间】:2015-07-27 16:14:59
【问题描述】:

我想使用openGL 来渲染QGraphicsview 项目,这样我可以节省CPU 功率。在文档中它指出我必须添加一个QOpenGLWidget 作为QGraphicsview 的视口。这就是我正在做的:

QOpenGLWidget *glWidget = new QOpenGLWidget();
ui->drawScreen->setViewport(glWidget);
ui->drawScreen->setViewportUpdateMode(QGraphicsView::FullViewportUpdate);
ui->drawScreen->update();

(ui->drawScreen是我的QgraphicsView)

当我在屏幕上绘制某些东西时,它会正确绘制,但经过一段时间后,我想使用淡入淡出动画移除该项目。这不会引起屏幕更新,即当我这样做时:

double opacity = 1.0 - ((elapsed - annotationFrameOut) / (double)fadeOutFrames);
(*i)->setOpacity(opacity);

(*i) 是一项。

或者这个:

scene.removeItem(item);

在视觉上,什么都没有发生。只有当我重新调整屏幕大小时,项目才会消失,或者显示正确的不透明度以防它褪色。

另外,当我移动一个项目时,没有位置消失,因此它会产生拖动效果。选择矩形或键入文本项时相同(边界矩形被绘制多次)。

这似乎是一个简单的更新问题,但我不知道该怎么办,我似乎也没有在网上找到这个问题。我正在使用 Windows。

感谢您的宝贵时间。

编辑: 举例说明问题的图片。蓝色矩形是永远不会删除的选择矩形(除非我重新调整窗口大小)

编辑 2: 代码使用QGLWidget

QGLWidget *viewPort = new QGLWidget(QGLFormat(QGL::SampleBuffers | QGL::AlphaChannel), ui->drawScreen);

ui->drawScreen->setViewport(viewPort);
ui->drawScreen->setViewportUpdateMode(QGraphicsView::FullViewportUpdate);
ui->drawScreen->update();

编辑 3: 在我的应用程序中,我在 QGraphicsView 下方播放了一段视频。每次出现新帧时,我都会通过更新 QLabel 来显示视频。

我没有使用QLabel,而是尝试更新QGraphicsPixmapImageQPixmap。如果现在我在此图像上绘制绘图正在正确刷新,我猜是因为图片正在不断更新。但是在图片之外它仍然不起作用。

【问题讨论】:

  • 您似乎没有更新您的窗口。您是否尝试过调用函数“update()”?它是 QOpenGLWidget 的一部分,继承自 QWidget。在您的paintGL() 或您更新程序主循环的任何地方调用该函数。
  • 我已经扩展了QGraphicsView 类。在其中,我有一个方法可以检查何时应该擦除绘制的项目(基于视频中的帧)。在那里我试图做viewport()->update() 或调用视图的update() 但它不起作用。没有openGL,这很好用(即使没有那个电话)。我是否必须扩展QOpenGLWidget 并实现我自己的paintGL?似乎不仅我的操作,而且任何意味着删除绘制的项目都不会更新(例如选择矩形)。
  • 我添加了一张图片来帮助说明这一点。
  • 调用 QOpenGLWidget 的 update() 函数。老实说,您应该绘制一个类图并决定是否要从 QOPenGLWidget 继承。对于它的价值,您将两个渲染 API 混合在一起。在这一点上,您必须问自己是否值得走 OpenGL 的低级车道(根本不是一件坏事)是否值得。为了减少一些 CPU 能力,我说使用图形视图而不是尝试让 GPU 来渲染它。
  • @Poriferous 手动调用update() 的建议是错误的。使用QGraphicsView 的全部意义在于这些事情是自动处理的。您关于“混合”两个渲染 API 的评论也是错误的 - Qt 完全支持在 OpenGL 上下文中使用 QPainter。这应该可以工作,而且确实可以与旧的QGLWidget 一起工作。

标签: c++ qt opengl qgraphicsview


【解决方案1】:

明确的update() 调用是不必要的。这看起来像一个 Qt 错误。 QGraphicsView does some magicQGLWidget 使其作为视口工作。很可能,这种魔法还没有被移植到QOpenGLWidget

作为一种解决方法,请改用QGLWidget

【讨论】:

  • 我尝试使用QGLWidget 并得到了相同的结果。我用的是QT5.5,这个版本有问题吗?
  • @Solidus 试试以前的版本吧。
  • 有趣的东西。我创建了一个不同的项目作为一个简单的例子。我基本上只是创建了一个QGraphicsView,一个QGraphicsScene,并添加了一个按钮来添加文本项和一个按钮来删除它。我将视图的视口设为QGLWidget,效果很好。这可能与我认为是继承类有关吗?另外,在我的项目中,当我使用openGL 时,背景会变黑。在这个小例子中,它保持白色。编辑:背景为黑色是因为我的视图是透明的。不过,在我的示例中它仍然可以很好地工作,所以这不是问题。
  • 我似乎找到了问题,并将其发布为答案。如果您知道为什么会导致此问题,我很想听听您的解释。 :) 感谢您的帮助。
  • 对不起,我想我开枪太早了,每次都还是不行。我已经用所发生的事情编辑了我的问题。
【解决方案2】:

看来问题出在我用来更改视图背景颜色的stylesheet 上。将stylesheet 添加到widget 也会产生相同的错误。使用stylesheet 时,视口会变成黑色,并且项目的刷新似乎无法正常工作。

我删除了stylesheet 并通过重新实现drawBackground 函数来更改背景颜色。

感谢 Kuba Ober 帮助我解决这个问题。

【讨论】:

    【解决方案3】:

    在某种程度上,样式表会产生重绘错误,即使在我的情况下,我已经删除了样式表并且一切正常。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-07-01
      • 1970-01-01
      • 2017-04-16
      相关资源
      最近更新 更多