如何使用插槽实时更新paint()

时间:2016-01-12 19:24:36

标签: c++ qt

我尝试为我的应用程序创建一些将实时更新的图例。我试过用一个插槽来做,但我得到了No such slot legend::paint()。 仅当我最小化然后最大化窗口时才更新图例。任何人都可以告诉我如何正确使用这个插槽来绘制圆圈作为图例中计数器的表示吗?

legend.cpp:

#include "legend.h"
#include <QGraphicsScene>
#include <QPainter>
#include <QDebug>
#include <QGraphicsItem>
#include <QTimer>
#include "player.h"

legend::legend(Player* player)
{
    this->player=player;
    timer = new QTimer(this);
    connect(timer, SIGNAL(timeout()), this, SLOT(paint()));
    timer->start(1);
}

QRectF legend::boundingRect() const
{
    return QRectF(0,0,350,350);
}

QPainterPath legend::shape() const
{
    QPainterPath path;
    path.addRect(0, 0, 350, 350);
    return path;
}

void legend::paint(QPainter *painter, const QStyleOptionGraphicsItem *, QWidget *)
{
    painter->setBrush(Qt::lightGray);
    painter->drawRect(0,0,350,350);


    painter->drawText(50,35,"COUNTER");
    for(int i = 0; i<10; i++)
    {
        if(player->getCounter()>i){
            painter->setBrush(Qt::yellow);
            painter->drawEllipse((i+1)*30,50,20,20);}
        else {
            painter->setBrush(Qt::lightGray);
            painter->drawEllipse((i+1)*30,50,20,20);
        }
    }
}

legend.h:

#ifndef LEGEND_H
#define LEGEND_H

#include <QGraphicsItem>
#include "player.h"

class legend : public QGraphicsObject
{
    Q_OBJECT

public:
    legend(Player* player);
    QPainterPath shape() const;
    QRectF boundingRect() const;
    QTimer *timer;
public slots:
    void paint(QPainter *painter, const QStyleOptionGraphicsItem *, QWidget *);
private:
    Player* player;
};

#endif // LEGEND_H

1 个答案:

答案 0 :(得分:1)

致电paint不是你的工作。 paint方法(不是插槽!)可供QGraphicsView用于渲染场景。

您应该做的是通知现场该项目已更新。将计时器连接到调用项目update上的插槽:

connect(timer, &QTimer::timeout, this, [this]{ update(); });

场景通知场景需要重新绘制,并最终根据需要调用paint方法。

您的计时器方式太快了。至少将超时更改为10 [ms]。

另一个问题:您正在为其计数器轮询Player实例。相反,Player对象应该通过信号广播计数器更改。通常,您将计数声明为Q_PROPERTY,然后您可以通过侦听属性更新信号让legend项跟随属性更改。