关于QT图形视图框架的问题

时间:2022-06-16 12:10:03
本人刚开始学习QT的图形视图框架,小试牛刀准备做一个小程序,实现在图片中显示一辆小车,并且小车还可以运行的效果,于是定义了两个类MapItem(继承QGraphicsPixmapItem)和CarItem(继承QGraphicsRectItem),然后把MapItem设置为CarItem的父图形项,这两个类我都重写了boundingRect()和paint()这两个函数,具体代码如下:
MapItem.h:
class MapItem: public QGraphicsPixmapItem
{
public:
    MapItem(QString file_Path);

    QRectF boundingRect() const;

    void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget);

    void setMap(QString file_path);
};


MapItem.cpp:
MapItem::MapItem(QString file_path)
{
    setMap(file_path);
    qDebug() << "MapItem construct finished!";
}

QRectF MapItem::boundingRect() const
{
    QRect rect = this->pixmap().rect();
    return QRectF(0, 0, rect.width(), rect.width());
}

void MapItem::paint(QPainter *painter, const QStyleOptionGraphicsItem*, QWidget*)
{
    qDebug() << "MapItem start painting!";
    QPixmap pix = this->pixmap();
    QRect rect = pix.rect();
    painter->drawPixmap(rect, pix);
}

void MapItem::setMap(QString file_path)
{
    QPixmap pix;
    pix.load(file_path);
    setPixmap(pix);
}


CarItem.h:
class CarItem: public QGraphicsRectItem
{
public:
    CarItem();
//    ~CarItem();

    QRectF boundingRect() const;

    void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget);

protected:
    void mousePressEvent(QGraphicsSceneMouseEvent* event);
    void hoverEnterEvent(QGraphicsSceneHoverEvent* event);

private:
    QString m_agv_name;


CarItem.cpp:
CarItem::CarItem()
{
    m_agv_name = "HeXieHao";
    setFlag(QGraphicsItem::ItemIsFocusable);
    setFlag(QGraphicsItem::ItemIsMovable);
    setAcceptHoverEvents(true);
    qDebug() << "CarItem construct finished!";
}

QRectF CarItem::boundingRect() const
{
    qreal width = this->rect().width();
    return QRectF(0, 0, width, width);
}

void CarItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget)
{
    qDebug() << "CarItem start painting!";
    if(hasFocus())
    {
        painter->setPen(Qt::red);
    }
    else
    {
        painter->setPen(QPen(QColor(0, 153, 0)));
    }
    painter->drawRect(-10, -10, 20, 20);
}

void CarItem::mousePressEvent(QGraphicsSceneMouseEvent *event)
{
    setFocus();
    setCursor(Qt::ClosedHandCursor);
}

void CarItem::hoverEnterEvent(QGraphicsSceneHoverEvent *event)
{
    setCursor(Qt::OpenHandCursor);
    setToolTip(m_agv_name);
}


然后我在widget.h中分别包含了MapItem、CarItem、和QGraphicsScene的成员变量:
widget.h:
class Widget : public QWidget
{
    Q_OBJECT

public:
    explicit Widget(QWidget *parent = 0);
    ~Widget();

    void start();

private:
    Ui::Widget *ui;
    MapItem m_map;
    AGVItem m_agv;
    QGraphicsScene m_scene;
};


最后在widget.cpp中这样实现(已经往widget.ui拖拽了一个QGraphicsView控件)
widget.cpp:
Widget::Widget(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::Widget),
    m_map("E:\\ZhouNiXing\\pic\\cmzw.jpg")
{
    ui->setupUi(this);
    m_scene.setSceneRect(-200, -150, 400, 300);
    m_agv.setParentItem(&m_map);
    m_scene.addItem(&m_map);
    m_map.setPos(-200, -150);
    ui->graphicsView->setScene(&m_scene);
    ui->graphicsView->show();
}

Widget::~Widget()
{
    delete ui;
}


我把代码都贴出来的原因是因为怕自己描述不清楚,最后导致的结果就是,编译没有问题,但是在关闭程序窗口之后,报了如下的错误:
关于QT图形视图框架的问题
请问这是由于什么原因导致的呢,我在网上查到有人说可能是在构造函数或者析构函数里面调用了纯虚函数,可是我这里都没有,实在找不到什么原因了,望有大神能帮我解答一下

2 个解决方案

#1


我把widget.h中的QGraphicsScene对象换成指针对象之后就没有这个问题了,代码如下:
class Widget : public QWidget
{
    Q_OBJECT

public:
    explicit Widget(QWidget *parent = 0);
    ~Widget();

    void start();

private:
    Ui::Widget *ui;
    MapItem m_map;
    AGVItem m_agv;
    QGraphicsScene* m_scene;
};

请问这是什么原因呢

#2


崩溃的时候在弹出的对话框按相应按钮进入调试,按Alt+7键查看Call Stack即“调用堆栈”里面从上到下列出的对应从里层到外层的函数调用历史。双击某一行可将光标定位到此次调用的源代码或汇编指令处, 看不懂时双击下一行,直到能看懂为止

#1


我把widget.h中的QGraphicsScene对象换成指针对象之后就没有这个问题了,代码如下:
class Widget : public QWidget
{
    Q_OBJECT

public:
    explicit Widget(QWidget *parent = 0);
    ~Widget();

    void start();

private:
    Ui::Widget *ui;
    MapItem m_map;
    AGVItem m_agv;
    QGraphicsScene* m_scene;
};

请问这是什么原因呢

#2


崩溃的时候在弹出的对话框按相应按钮进入调试,按Alt+7键查看Call Stack即“调用堆栈”里面从上到下列出的对应从里层到外层的函数调用历史。双击某一行可将光标定位到此次调用的源代码或汇编指令处, 看不懂时双击下一行,直到能看懂为止