2011-09-15 29 views
8

Escribí una clase derivada de QGraphicsScene. En un punto, necesito eliminar todos los elementos de la escena y quiero que los artículos se destruyan físicamente (llamada del destructor). He intentado lo siguiente:Cómo eliminar todo QGraphicsItem de QGraphicsScene

QList<QGraphicsItem*> all = items(); 
for (int i = 0; i < all.size(); i++) 
{ 
    QGraphicsItem *gi = all[i]; 
    removeItem(gi); 
    delete gi; // warning at this line 
} 

Qt Creator emite una advertencia: Advertencia: C4150: supresión del puntero al tipo incompleto 'QGraphicsItem'; no destructor llamado

No estoy seguro de por qué es eso. QGraphicsItem tiene un destructor virtual por lo que los elementos se deben eliminar de la memoria.

Si este no es el camino correcto, ¿cómo puedo eliminar todos QGraphicsItem s de QGraphicsScene? Tenga en cuenta que sé que cuando se elimine la escena, todos los elementos también se eliminarán. Pero quiero eliminar elementos de la escena y dibujar otros elementos. Quiero que los elementos eliminados se eliminen de la memoria.

Respuesta

7

Tienes que

#include <QGraphicsItem> 

en ese archivo. De lo contrario, el compilador no sabe qué QGraphicsItem es decir, que tiene un destructor virtual, etc.

9

Como jpalecek señaló, se echa en falta el archivo de cabecera. Deberías aceptar su respuesta. Solo voy a señalar dos posibles problemas:

Antes que nada, no necesita llamar al QGraphicsScene::removeItem(). QGraphicsItem::~QGraphicsItem() hace eso por usted.

En segundo lugar. Tenga cuidado si coloca QGraphicsItem dentro de otros. Es decir, tiene elementos que son hijos de otros artículos. El destructor de QGraphicsItem elimina automáticamente todos sus elementos secundarios. Por lo tanto, cuando recorra los elementos devueltos desde QGraphicsScene, puede terminar borrando un elemento secundario que ya ha sido eliminado por su principal. Por ejemplo, supongamos que tiene 2 elementos, A y B, y B es hijo de A. Cuando elimina A, B se elimina automáticamente. Y luego llegas a B e intentas eliminarlo. ¡AUGE!

Una forma más segura de hacer esto es para probar si el artículo es el nivel superior uno, es decir, que no tiene padre:

QList<QGraphicsItem*> all = items(); 
for (int i = 0; i < all.size(); i++) 
{ 
    QGraphicsItem *gi = all[i]; 
    if(gi->parentItem()==NULL) { 
     delete gi; 
    } 
} 
Cuestiones relacionadas