如何在离开boundingRect后删除QGraphicsitems

How to remove QGraphicsitems after leaving boundingRect

本文关键字:删除 QGraphicsitems boundingRect 离开      更新时间:2023-10-16

我以为我可以用下面的代码在任何项目离开场景后删除它,但事实并非如此。在尝试了不同的实现之后,我认为我应该尝试另一种方法。有些QGraphicsItem实际上是在boundingRect之外开始的,所以我想知道是否有办法在GraphicsItem经过某个坐标点后删除它们。

void Scene::advance()
{
        QList <QGraphicsItem *> itemsToRemove;
        foreach( QGraphicsItem * item, this->items())
        {
            if( !this->sceneRect().intersects(item->boundingRect()))
            {
                // The item is no longer in the scene rect, get ready to delete it
                itemsToRemove.append(item);
            }                
        }
        foreach( QGraphicsItem * item, itemsToRemove )
        {
            this->removeItem(item);
            delete(item);
        }    
        QGraphicsScene::advance();
}

问题出在这一行:-

 if( !this->sceneRect().intersects(item->boundingRect()))

这是比较场景坐标中的场景矩形和项目局部坐标系中的项目边界矩形。

您需要转换其中一个,以便在同一坐标系内进行比较。

 QRectF itemSceneBoundingRect = item->mapRectToScene(item->boundingRect());
 if( !this->sceneRect().intersects(itemSceneBoundingRect)
 {
      // remove the item.
 }

您可以保存每个项目的状态并跟踪状态更改。你可以在两个QVector中沿着它们的状态放置项目,比如:

QVector<QGraphicsItem *> items;
QVector<bool> itemIsInBoundingRect; // whether item is boundingrect or not

并更新其状态并跟踪状态变化:

void Scene::advance()
{
        for(int i=0;i<items.count();i++)
        {
            if(this->sceneRect().intersects(items[i]->boundingRect()))
            {
                // The item is in scene rect
                itemIsInBoundingRect[i] = true;
            }
            else // The item is in not in scene rect
            {
                if(itemIsInBoundingRect[i]) // track state change
                {
                     this->removeItem(items[i]);
                     delete(items[i]);
                     items.remove(i);
                     itemIsInBoundingRect.remove(i);
                }
            }                
        }
        QGraphicsScene::advance();
}