Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Drag and Drop in QAbstractItemModel PySide PyQt

I have been chipping away at learning how to implement QAbstractItemModel with QTreeView, and a custom Item class, and I have everything working except for the drag and drop.

Ultimately I would like to be able to switch between Moving and Copying items with the shift Key, but for now I am just trying to get the InternalMove to work at all....

I am re-implementing mimeData and dropMimeData like this....

class BuildModel( QAbstractItemModel ):
    def __init__( self, root):
        super( BuildModel, self ).__init__()

    def mimeTypes( self ):
        return ['sushi-build-items']

    def mimeData( self, indices ):
        mimedata = QMimeData()
        mimedata.setData('sushi-build-items', self.getSerializedData(indices) )
        return mimedata

    def dropMimeData( self, mimedata, action, row, column, parentIndex ):
        if not mimedata.hasFormat( 'sushi-build-items' ):
            return False
        data = pickle.loads((str(mimedata.data('sushi-build-items'))))
        items = dataToItems(data)
        self.insertItems(row, items, parentIndex)
        return True

    def insertItems( self, row, items, parentIndex):
        parent = self.itemFromIndex(parentIndex)
        self.beginInsertRows( parentIndex, row, row+len(items)-1 )
        if row == -1:
            parent.addChildren(items)
        else:
            parent.insertChildren(row, items)
        self.endInsertRows()
        self.dataChanged.emit(parentIndex, parentIndex)
        return True

And my tree view is set to InternalMove like this....

class TreeView(QTreeView):
    def __init__(self, parent = None, model = None):

        super(TreeView, self).__init__(parent = parent)
        self.setDragDropMode(QAbstractItemView.InternalMove)
        self.setDragEnabled(True)
        self.setAcceptDrops(True)

But when I drag and drop the source item stays as it is, and it just drops a duplicate item. Shouldn't the removal of the dragged item be handled by the TreeView? If not where do I remove it manually?

I am convinced I am missing something here..

like image 335
Pax Avatar asked Oct 21 '22 11:10

Pax


1 Answers

You need to implement the removeRows method in your model; it should get called automatically.

like image 105
Sydius Avatar answered Oct 23 '22 08:10

Sydius