c++qtdrag-and-dropqabstractitemmodelqabstractitemview

Qt: Attempt to add Drag and Drop to Editable Tree Model example not working


I'm trying to learn how to implement Drag and Drop to model/view settings in Qt. As an exercise, I attempted to do that to the Editable Tree Model example available at the Qt web site:

Editable Tree Model

To extend it with Drag and Drop, I followed the instructions in Qt's documentation on "Using Drag and Drop with View Items", more specifically "Using model/view classes".

I placed the code for my attempt at a GitHub repository. The main modifications are below but there are other important ones; here are the full changes according to the documentation.

/* mainwindow.cpp -- THIS IS NOT ALL CHANGES -- See link above for all changes */
view->setSelectionMode(QAbstractItemView::SingleSelection);
view->setDragEnabled(true);
view->viewport()->setAcceptDrops(true);
view->setDropIndicatorShown(true);
view->setDragDropMode(QAbstractItemView::DragDrop);

However, this didn't quite work. While I can drag and drop items, the copied item appears as blank. This can be seen in this screen capture, but the main screenshots are:

Dragging "Getting Started" on "Composing the Dialog"

Results in a blank item

Note that the documentation describes the need to re-implement QAbstractItemModel's dropMimeData for drag and drop functionality, which I did not. This is because, upon inspecting the source code for that class, I find that its default implementation should already work in copying items in drag and drop, since it uses the default application/x-qabstractitemmodeldatalist MIME format and uses setItemData for the inserted items.

What is wrong here? Is it the default dropMimeData that's not working, or something else?


Solution

  • The model provided by the example only accepts setting data with role Qt::EditRole. See line 263 in treemodel.cpp

    bool TreeModel::setData(const QModelIndex &index, const QVariant &value, int role)
    {
        if (role != Qt::EditRole)
            return false;
    
        ...
    }
    

    Removing that part or adding Qt::DisplayRole and the data will be set properly.