调用更新后保存QPainter

时间:2018-07-03 02:12:03

标签: qt qml qt5

我想在qml上画直线,但是每次画线时,前一条消失了,我想知道它是否与update方法有关,是否有解决此问题的方法。

main.qml

MouseArea{
    id:fidpoint
    anchors.fill: parent
    onPressed: {
        switch(addstate.currentText){
        case 'Track':
            map.setTstart(mouseX,mouseY);
            draw_line.setColor("black");
            draw_line.setStart(Qt.point(mouseX,mouseY));
            draw_line.setEnd(Qt.point(mouseX,mouseY));
            draw_line.update();
            break;
        }
    }
    onReleased: {
        switch(addstate.currentText){
        case 'Track':
            map.addTrack(mouseX,mouseY);
            draw_line.setColor("black");
            draw_line.setEnd(Qt.point(mouseX,mouseY));
            draw_line.update();
            break;
        }
    }
    onPositionChanged: {
        switch(addstate.currentText){
        case 'Track':
            draw_line.setColor("black");
            draw_line.setEnd(Qt.point(mouseX,mouseY));
            draw_line.update();
            break;
        }
    }
}

draw_line是我从main.cpp向qml注册的对象的ID

paint.cpp

void Paint::paint(QPainter *painter)
{
    QPen pen(m_color, 2);
    painter->setPen(pen);
    painter->setRenderHint(QPainter::Antialiasing,true);
    painter->drawLine(startNode,endNode);
}

paint是继承自QQuickPaintedItem

的类

1 个答案:

答案 0 :(得分:0)

可能的选择是创建一个图像并将更改保存在那里,但这将在短期内解决您的问题。更好的选择是draw_line仅绘制一条线,然后将其添加为您希望画布成为的项的子项。

lineitem.h

#ifndef LINEITEM_H
#define LINEITEM_H

#include <QQuickPaintedItem>

class LineItem: public QQuickPaintedItem
{
    Q_OBJECT
    Q_PROPERTY(QPoint startPos READ startPos WRITE setStartPos NOTIFY startPosChanged)
    Q_PROPERTY(QPoint endPos READ endPos WRITE setEndPos NOTIFY endPosChanged)
    Q_PROPERTY(QColor lineColor READ lineColor WRITE setLineColor NOTIFY lineColorChanged)
public:
    using QQuickPaintedItem::QQuickPaintedItem;
    void paint(QPainter *painter);

    QPoint startPos() const;
    void setStartPos(const QPoint &startPos);
    QPoint endPos() const;
    void setEndPos(const QPoint &endPos);
    QColor lineColor() const;
    void setLineColor(const QColor &lineColor);

signals:
    void startPosChanged();
    void endPosChanged();
    void lineColorChanged();

private:
    QPoint m_startPos;
    QPoint m_endPos;
    QColor m_lineColor;
};

#endif // LINEITEM_H

lineitem.cpp

#include "lineitem.h"

#include <QPainter>

void LineItem::paint(QPainter *painter)
{
    painter->setRenderHint(QPainter::Antialiasing, true);
    QPen pen(m_lineColor, 2);
    painter->setPen(pen);
    painter->drawLine(m_startPos, m_endPos);
}

QPoint LineItem::startPos() const
{
    return m_startPos;
}

void LineItem::setStartPos(const QPoint &startPos)
{
    if(m_startPos == startPos)
        return;
    m_startPos = startPos;
    emit startPosChanged();
    update();
}

QPoint LineItem::endPos() const
{
    return m_endPos;
}

void LineItem::setEndPos(const QPoint &endPos)
{
    if(m_endPos == endPos)
        return;
    m_endPos = endPos;
    emit endPosChanged();
    update();
}

QColor LineItem::lineColor() const
{
    return m_lineColor;
}

void LineItem::setLineColor(const QColor &lineColor)
{
    if(m_lineColor == lineColor)
        return;
    m_lineColor = lineColor;
    emit lineColorChanged();
    update();
}

main.qml

import QtQuick 2.9
import QtQuick.Window 2.2

import com.eyllanesc.org 1.0

Window {
    id: win
    visible: true
    width: 640
    height: 480
    title: qsTr("Hello World")

    property LineItem currentItem: null

    Rectangle{
        id: canvas
        anchors.fill: parent

        MouseArea{
            anchors.fill: parent

            onPressed: {
                currentItem = create_lineitem(canvas)
                currentItem.lineColor = "green"
                currentItem.anchors.fill = canvas
                currentItem.startPos = Qt.point(mouseX,mouseY)
                currentItem.endPos = Qt.point(mouseX,mouseY)
            }
            onReleased:  currentItem.endPos = Qt.point(mouseX,mouseY)
            onPositionChanged: currentItem.endPos = Qt.point(mouseX,mouseY)
        }
    }

    function create_lineitem(parentItem, color) {
        return Qt.createQmlObject('import com.eyllanesc.org 1.0; LineItem{}',
                                           parentItem);
    }

}

main.cpp

#include "lineitem.h"

#include <QGuiApplication>
#include <QQmlApplicationEngine>

int main(int argc, char *argv[])
{
    QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);

    QGuiApplication app(argc, argv);

    qmlRegisterType<LineItem>("com.eyllanesc.org", 1, 0, "LineItem");

    QQmlApplicationEngine engine;
    engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
    if (engine.rootObjects().isEmpty())
        return -1;

    return app.exec();
}

enter image description here

完整的示例可以在下面的link中找到。