如何修复“创建的图形对象未放置在图形场景中”的错误
Posted
技术标签:
【中文标题】如何修复“创建的图形对象未放置在图形场景中”的错误【英文标题】:How can I fix the error saying Created graphical object was not placed in the graphics scene 【发布时间】:2018-04-25 00:24:13 【问题描述】:一个看似简单的问题导致了一个奇怪的错误。
在我的源代码中,我尝试使用 QQuickPaintedItem 来呈现 QWidget 派生类 (QPushButton) 的整体外观,然后将其绘制到 QQuickPaintedItem
这样做我遇到了这个错误:
QQmlComponent: 创建的图形对象没有放在图形中 场景。
接着是:
程序意外结束。
这是我尝试创建我的特殊 QQuickPaintedItem 的上下文以及它的源代码:
main.qml
import QtQuick 2.9
import com.particletool 1.0
import QtQuick.Particles 2.0
import QtQuick.Window 2.3
import QtQuick.Controls 2.2
import QtQuick.Dialogs 1.2
import QtQuick.Controls 1.4 as QQ1
Item
id: root
width: Screen.width
height: Screen.height
WidgetInterface
id: w
widgetInterface.h
#ifndef WIDGETINTERFACE_H
#define WIDGETINTERFACE_H
#include <QObject>
#include <QQuickItem>
#include <QQuickPaintedItem>
#include <QWidget>
#include <QPushButton>
#include <QtQuick>
class WidgetInterface : public QQuickPaintedItem
public:
WidgetInterface(QQuickItem *parent = nullptr, QWidget* renderWidget = nullptr);
QWidget* m_widget;
QPushButton* m_button;
protected:
void paint(QPainter* painter);
public slots:
void morphIntoButton(QString txt);
;
#endif // WIDGETINTERFACE_H
widgetinterface.cpp
#include "widgetinterface.h"
#include <QQuickPaintedItem>
#include <QObject>
#include <QPainter>
#include <QWidget>
#include <QPushButton>
WidgetInterface::WidgetInterface(QQuickItem *parent, QWidget* renderWidget) : QQuickPaintedItem(parent), m_widget(renderWidget)
morphIntoButton("test");
QQmlEngine::setObjectOwnership(m_button, QQmlEngine::javascriptOwnership);
void WidgetInterface::paint(QPainter *painter)
if (m_widget != nullptr)
painter->end();
m_button->render(painter);
else
void WidgetInterface::morphIntoButton(QString txt)
m_widget->setGeometry(0,0, this->width(), this->height());
m_button = new QPushButton(m_widget);
m_button->setGeometry(m_widget->geometry());
m_button->setText(txt);
this->update(this->boundingRect().toRect());
main.cpp
#include <QtGui/QGuiApplication>
#include <QApplication>
#include <QtQml/QQmlApplicationEngine>
#include "src/interfaces/widgetinterface.h"
int main(int argc, char *argv[])
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
QGuiApplication app(argc, argv);
QQmlApplicationEngine engine;
qmlRegisterType<WidgetInterface>("com.particletool", 1, 0, "WidgetInterface");
engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
if (engine.rootObjects().isEmpty())
return -1;
return app.exec();
预期的结果是在 QML 场景图上绘制一个按钮 有谁知道我如何使用某种方法来实现这一目标? (我知道 Qt 不支持它,但我正在尝试实现一种方法来实现它,所以不要同时使用“你不能”的答案,因为我确定有一种方法。
【问题讨论】:
出于本示例的目的在 Widget 接口构造函数中。但最终目标是通过包含像 Qt.Widgets 这样的单个库,以无缝方式在 QML 中实现所有基于 QWidget 的元素1.0什么的 【参考方案1】:预期的结果是在 QML 场景图上绘制一个按钮
class WidgetInterface : public QQuickPaintedItem
public:
WidgetInterface(QQuickItem *parent = Q_NULLPTR) :
QQuickPaintedItem(parent)
mButton = new QPushButton("TEST", Q_NULLPTR);
auto resize = [=]()
mButton->setGeometry(QRect(QPoint(), boundingRect().size().toSize()));
QPixmap p(mButton->size());
mButton->render(&p);
if(!p.isNull())
mButtonPix = p;
update();
;
connect(this, &QQuickPaintedItem::widthChanged, this, resize, Qt::QueuedConnection);
connect(this, &QQuickPaintedItem::heightChanged, this, resize, Qt::QueuedConnection);
~WidgetInterface()
mButton->deleteLater();
protected:
void paint(QPainter* painter)
painter->drawPixmap(0, 0, mButtonPix);
private:
QPushButton* mButton;
QPixmap mButtonPix;
;
【讨论】:
以上是关于如何修复“创建的图形对象未放置在图形场景中”的错误的主要内容,如果未能解决你的问题,请参考以下文章
分段错误错误(信号名称:SIGSEGV)的原因是啥,我将如何找到/修复它?