Смешанные родительские и дочерние узлы, используя QTreeWidget (Qt4) и drag'n'drop - PullRequest
0 голосов
/ 16 июля 2011

Я использую QTreeWidget для отображения дерева родительских узлов с их оставленными узлами.Каждый родитель может иметь различные конечные узлы, но конечные узлы не должны иметь дочерних узлов.Пользователь должен иметь возможность перемещать листья между родителями, перетаскивая их на новую позицию.Чтобы не сбрасывать листья на другие листья, я установил ItemIsDragEnabled на листьях, а ItemIsDropEnabled на родительских узлах.Это прекрасно работает, если QTreeWidget установлен в «SingleSelection».Однако, если для SelectionMode задано значение ExtendedSelection, вы можете выбрать отпуск и родительский узел и поместить их оба на лист: http://i.stack.imgur.com/Kil3y.jpg (снимок экрана)

Вот примеркод:

QTreeWidget *tree = this->ui->treeWidget;
QTreeWidgetItem *item;
QTreeWidgetItem *child;
tree->setSelectionMode(QAbstractItemView::ExtendedSelection);
tree->setDefaultDropAction(Qt::MoveAction);
tree->setDragEnabled(true);
tree->setAcceptDrops(true);
tree->setDropIndicatorShown(true);

// disable dropping of leaves as top level items
tree->invisibleRootItem()->setFlags( Qt::ItemIsSelectable |
                Qt::ItemIsUserCheckable | Qt::ItemIsEnabled );

for (int i = 0; i < 2; i++) {
    // create top level item
    item = new QTreeWidgetItem();
    item->setText(0, "parent");
    item->setFlags(Qt::ItemIsSelectable | Qt::ItemIsUserCheckable
                  | Qt::ItemIsDropEnabled | Qt::ItemIsEnabled );

    // add 3 child items
    for (int j = 0; j < 3; j++) {
        child = new QTreeWidgetItem();
        child->setText(0, "child");
        child->setFlags(Qt::ItemIsSelectable | Qt::ItemIsUserCheckable
                      | Qt::ItemIsDragEnabled | Qt::ItemIsEnabled );
        item->addChild(child);
    }

    // add item to tree
    tree->addTopLevelItem(item);
}

Я много гуглил, но не смог найти решение.Как я могу сохранить дочерние и родительские узлы на соответствующих уровнях при использовании ExtendedSelection?

Нужно ли создавать подкласс QTreeWidget и переопределять insertRows ()?Есть ли способ перехватить действия drag'n'drop на QTreeWidget, чтобы я мог проверить, нормально ли это действие?(Если есть способ заставить это работать с QStandardItemModel / QTreeView, я тоже был бы счастлив)

1 Ответ

0 голосов
/ 08 марта 2012

Один простой обходной путь - подключить небольшую функцию к сигналу itemSelectionChanged, которая удаляет все элементы из выбора, которые не относятся к тому типу, который был выбран последним.Работает просто идеально для меня (и для других программ, таких как редактор триггера Warcraft 3)

...