【问题标题】:QGraphicsLineItem::paint() artifactsQGraphicsLineItem::paint() 工件
【发布时间】:2012-12-05 16:51:13
【问题描述】:

我有自己的类,它继承自 QGraphicsLineItem 并覆盖 paint() 方法以绘制带有箭头的粗线:

void MyGraphicsItem::paint( QPainter* aPainter,
                            const QStyleOptionGraphicsItem* aOption,
                            QWidget* aWidget /*= nullptr*/ )
{
    Q_UNUSED( aOption );
    Q_UNUSED( aWidget );

    QLineF cLine = line();

    aPainter->setPen( QPen( Qt::black, 6, Qt::SolidLine ) );
    aPainter->drawLine( cLine );

    qreal lineAngle = cLine.angle();

    const qreal radius = 2.0;
    QLineF head1 = cLine;
    head1.setAngle(lineAngle+32);
    head1.setLength( 12 );
    QLineF head2 = cLine;
    head2.setAngle(lineAngle-32);
    head2.setLength( 12 );

    aPainter->drawLine( head1 );
    aPainter->drawLine( head2 );

    aPainter->setPen( QPen( Qt::yellow, 2, Qt::SolidLine ) );

    aPainter->drawLine( cLine );

    aPainter->drawLine( head1 );
    aPainter->drawLine( head2 );
}

当我在场景周围绘制项目时,这似乎会导致渲染伪影。据我所知,因为我在QPen 上设置了厚度,这让我相信我必须以某种方式在项目矩形之外绘制?

是什么导致了我的渲染问题,我该如何解决?

请注意图像中的背景没有被重绘 - 这发生在场景中箭头也被拖过的任何其他对象上。

编辑:我认为这实际上是我的问题:

Subclassing QGraphicsView and setting drawBackground

再次编辑:似乎绘制背景是问题所在,但使用全视图端口更新会降低性能,所以我想出了这个方法,它似乎将 CPU 使用率保持在 3%,而不是将一个核心与 100% 使用率挂钩。

// This code lives in the QGraphicsScene constructor, doesn't have to be there though since QGraphicsScene::setBackgroundBrush is public.
int gridSizeX = 25;
int gridSizeY = 20;
QImage singleGrid( gridSizeX, gridSizeY, QImage::Format_RGB32 );
singleGrid.fill( Qt::white );
{
    QPainter painter( &singleGrid );

    // Lighter background
    painter.setPen( QPen( QColor( 240, 240, 240 ) ));

    qreal midx = gridSizeX / 2;
    qreal midy = gridSizeY / 2;
    painter.drawLine( 0, midy, gridSizeX, midy );
    painter.drawLine( midx, 0, midx, gridSizeY );

    // Darker foregound
    painter.setPen( QPen( QColor( 180, 180, 180 ) ));
    painter.drawRect( 0, 0, gridSizeX, gridSizeY );

    painter.end();
}
QBrush brushBackground( singleGrid );
setBackgroundBrush( brushBackground );

场景然后在各处重复此笔刷,从而产生相同的网格背景效果,甚至在缩放/缩放时也能按预期工作。 :)。

【问题讨论】:

    标签: c++ qt qt4 qgraphicsitem


    【解决方案1】:

    当您覆盖paint() 函数时,您还需要在您的类中覆盖QGraphicsItem::boundingRect() 以定义您的自定义图形项的外部边界。如果你在边界之外绘制,你最终会得到渲染工件。现在你依赖于 QGraphicsLineItem 的 boundingRect() 实现,它当然不知道你的paint() 函数的实现。详情请见http://doc.qt.digia.com/main-snapshot/qgraphicsitem.html#boundingRect

    【讨论】:

    • 谢谢,我把边界矩形做得很大,但我仍然在网格背景的箭头底部看到奇怪的人工制品,有什么想法吗?
    • 接受你的回答,因为我的边界在哪里出错,即使这不是我问题的根本原因。
    • 只是出于好奇,还有什么问题?
    • 与链接的问题相同,如果您绘制自定义背景,则默认场景更新模式不会重绘背景,因此使用我上面的技巧可以避免使用缓慢的全场景重绘。希望这是有道理的!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-07-27
    • 2019-04-18
    • 2015-04-22
    • 1970-01-01
    • 1970-01-01
    • 2016-08-09
    相关资源
    最近更新 更多