我目前正在使用Qt在C++中为学校开发小型游戏/模拟游戏,并且对Java有一定的了解。我的问题是如何在800/600窗口中使用Qt设置基本的游戏循环。我尝试使用覆盖paintEvent的方式绘制到GraphicsView窗口中,但无法建立这样的循环,并且在覆盖它方面存在某种错误。
#include "mainwindow.h"
#include <QGraphicsView>
#include "graphicsview.h"
MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent)
{
resize(800, 600);
setWindowTitle("A* Pathfinder");
gView = new GraphicsView(this);
setCentralWidget(gView);
}
MainWindow::~MainWindow()
{
}
GraphicsView类:
#include "graphicsView.h"
void GraphicsView::paintEvent(QPaintEvent *event) {
QPainter painter(this);
painter.drawLine(10,10, 100,100);
}
graphicsView.h:
#ifndef GRAPHICSVIEW_H
#define GRAPHICSVIEW_H
#endif // GRAPHICSVIEW_H
#include <QGraphicsView>
class GraphicsView : public QGraphicsView
{
protected:
void paintEvent(QPaintEvent *event);
};
抱歉,是否有人提出过类似的问题,但我真的很困,无法针对我的具体情况寻求帮助。同样,我想要一个800x600的窗口,可以在其中以30fps的速度绘制图形。
最佳答案
首先,您要朝错误的方向前进-您不需要重写QGraphicsView
即可满足需求。您不需要覆盖paintEvent()
-不会执行您认为的操作。您不在那里渲染场景,那是仅渲染 View 框架的代码-空 View 的外观,而不是 View 包含的内容。
如果您有自定义图形,而图形项目(例如矩形,文本,圆弧和其他图形)没有提供此自定义图形,则您需要实现自己的QGraphicsItem
并实现其paint()
函数-这就是它的工作方式,每个项目都负责其绘画,场景仅管理所有项目, View 仅使场景可视化。
您绝对不希望计时器以固定的速率触发,这是非常幼稚且较差的解决方案。它不考虑渲染和游戏逻辑处理所花费的时间,并且如果您想要稳定的帧速率,则必须考虑这些变量。
30 FPS意味着您必须每33.33毫秒移动一帧。因此,您需要根据前一个帧花费的时间来调度每个后续帧。例如,如果上一帧花费了15毫秒,那么您就需要在33.33 - 15
毫秒中安排下一帧,只要您的CPU能够保持同步,就可以实现更精细的控制和稳定的帧速率。
您可以使用静态函数QTimer::singleShot()
来以自定义间隔安排每个后续帧。