void objects_tree::dropEvent(QDropEvent * event) { QModelIndex index = indexAt(event->pos()); if (!index.isValid() ) return; QTreeWidgetItem* dest = itemFromIndex(index); if (!dest) return; std::vector<int> from; auto selected = selectedItems(); foreach(QTreeWidgetItem *s, selected) { if (s->parent() != dest->parent()) return; from.push_back(s->parent()->indexOfChild(s)); } int to = index.row(); if (dropIndicatorPosition() == QAbstractItemView::BelowItem) ++to; std::string group = to_str(dest->parent()->text(0)); m_parent->reorder_objects(group, from, to); event->acceptProposedAction(); }
void SceneTree::dragMoveEvent(QDragMoveEvent *event) { QTreeView::dragMoveEvent(event); int row = -1; int col = -1; QModelIndex index = indexAt(event->pos()); switch (dropIndicatorPosition()) { case QAbstractItemView::AboveItem: row = index.row(); col = index.column(); index = index.parent(); break; case QAbstractItemView::BelowItem: row = index.row() + 1; col = index.column(); index = index.parent(); break; case QAbstractItemView::OnItem: case QAbstractItemView::OnViewport: break; } if(!treeModel->DropCanBeAccepted(event->mimeData(), event->dropAction(), row, col, index)) { event->ignore(); } }
void GroupView::dragMoveEvent(QDragMoveEvent* event) { if (event->keyboardModifiers() & Qt::ControlModifier) { event->setDropAction(Qt::CopyAction); } else { event->setDropAction(Qt::MoveAction); } QTreeView::dragMoveEvent(event); // entries may only be dropped on groups if (event->isAccepted() && event->mimeData()->hasFormat("application/x-keepassx-entry") && (dropIndicatorPosition() == AboveItem || dropIndicatorPosition() == BelowItem)) { event->ignore(); } }
void TTreeWidget::dropEvent(QDropEvent *event) { QTreeWidgetItem * pItem = itemAt( event->pos() ); if( ! pItem ) { event->setDropAction( Qt::IgnoreAction ); event->ignore(); } if( pItem == topLevelItem(0) ) { if( (dropIndicatorPosition() == QAbstractItemView::AboveItem ) || (dropIndicatorPosition() == QAbstractItemView::BelowItem ) ) { event->setDropAction( Qt::IgnoreAction ); event->ignore(); } } if ( mIsVarTree ) { LuaInterface * lI = mpHost->getLuaInterface(); if ( ! lI->validMove( pItem ) ) { event->setDropAction( Qt::IgnoreAction ); event->ignore(); } QTreeWidgetItem * newpItem = pItem; QTreeWidgetItem * cItem = selectedItems().first(); QTreeWidgetItem * oldpItem = cItem->parent(); if ( ! lI->reparentVariable( newpItem, cItem, oldpItem ) ) { qDebug()<<"reparent failed"; event->setDropAction( Qt::IgnoreAction ); event->ignore(); } } mIsDropAction = true; QTreeWidget::dropEvent( event ); return; }
void TTreeWidget::dropEvent(QDropEvent *event) { QTreeWidgetItem * pItem = itemAt( event->pos() ); if( ! pItem ) { event->setDropAction( Qt::IgnoreAction ); event->ignore(); } if( pItem == topLevelItem(0) ) { if( (dropIndicatorPosition() == QAbstractItemView::AboveItem ) || (dropIndicatorPosition() == QAbstractItemView::BelowItem ) ) { event->setDropAction( Qt::IgnoreAction ); event->ignore(); } } mIsDropAction = true; QTreeWidget::dropEvent( event ); return; }
bool HierarchyTreeControl::GetMoveItemID(QDropEvent *event, HierarchyTreeNode::HIERARCHYTREENODEID &insertInTo, HierarchyTreeNode::HIERARCHYTREENODEID &insertAfter) { DropIndicatorPosition position = dropIndicatorPosition(); QTreeWidgetItem* item = itemAt(event->pos()); if (!item) return false; if (item == currentItem()) return false; insertInTo = HierarchyTreeNode::HIERARCHYTREENODEID_EMPTY; switch (position) { case OnViewport: { return false; }break; case OnItem: { QVariant data = item->data(ITEM_ID); insertInTo = data.toInt(); insertAfter = HierarchyTreeNode::HIERARCHYTREENODEID_EMPTY; } break; case AboveItem: { QTreeWidgetItem* parent = item->parent(); if (parent) insertInTo = parent->data(ITEM_ID).toInt(); QTreeWidgetItem* above = itemAbove(item); if (!above) return false; insertAfter = above->data(ITEM_ID).toInt(); } break; case BelowItem: { QTreeWidgetItem* parent = item->parent(); if (parent) insertInTo = parent->data(ITEM_ID).toInt(); insertAfter = item->data(ITEM_ID).toInt(); }break; } if (currentItem() && currentItem()->data(ITEM_ID) == insertAfter) return false; return true; }
void HierarchyTreeControl::HandleDragMoveControlMimeData(QDragMoveEvent *event, const ControlMimeData* /*mimeData*/) { DropIndicatorPosition position = dropIndicatorPosition(); Logger::Warning("POSITION TYPE^ %i", position); // Where we are in tree? QTreeWidgetItem* item = itemAt(event->pos()); if (!item) { HierarchyTreeController::Instance()->ResetSelectedControl(); return; } HierarchyTreeNode::HIERARCHYTREENODEID insertInto = HierarchyTreeNode::HIERARCHYTREENODEID_EMPTY; QVariant data = item->data(ITEM_ID); insertInto = data.toInt(); // Handle specific types of nodes. HierarchyTreeNode* nodeToInsertControlTo = HierarchyTreeController::Instance()->GetTree().GetNode(insertInto); if (dynamic_cast<HierarchyTreePlatformNode*>(nodeToInsertControlTo) || dynamic_cast<HierarchyTreeAggregatorControlNode*>(nodeToInsertControlTo)) { // Don't allow to drop the controls directly to Platform or Aggregator. HierarchyTreeController::Instance()->ResetSelectedControl(); return; } // Expand the items while dragging control on them. if (!item->isExpanded()) { item->setExpanded(true); } scrollTo(indexAt(event->pos())); HierarchyTreeControlNode* controlNode = dynamic_cast<HierarchyTreeControlNode*>(nodeToInsertControlTo); if (controlNode) { // Don't reselect the same control, if it is already selected. if (!HierarchyTreeController::Instance()->IsControlSelected(controlNode)) { HierarchyTreeController::Instance()->ResetSelectedControl(); HierarchyTreeController::Instance()->SelectControl(controlNode); } } event->accept(); }
void FileOrganiserWidget::dragMoveEvent(QDragMoveEvent *pEvent) { // Set the state to dragging, since we can only come here when dragging // Note: the state is properly set for file organiser objects being dragged, // but should we be dragging external objects over our file organiser // widget, then the state will (obviously) not be set. This wouldn't // be a problem in itself if it was for the fact that this prevents // the drop indicator from being painted, so... setState(QAbstractItemView::DraggingState); // Default handling of the event // Note: this gives us the drop indicator... TreeViewWidget::dragMoveEvent(pEvent); // Accept the proposed action for the event, but only if there are objects // to drop and if we are not trying to drop the objects above/on/below one // of them (should the objects come from the file organiser widget) or on a // file item // Note #1: for the number of objects being dropped, we have to check the // number of URLs information (i.e. external objects), as well as // the MIME data associated with FileOrganiserMimeType (i.e. // objects from the file organiser widget, after we have ) // Note #2: for the dropping location, it can be either a folder or a file // (as long as the indicator position isn't on the item itself), // but not above/on/below any of the objects (or any of their // children) being dragged (only relevant when dragging items from // the file organiser widget) QByteArray data = pEvent->mimeData()->data(FileOrganiserMimeType); QModelIndexList indexes = mModel->decodeData(data); QStandardItem *dropItem = mModel->itemFromIndex(indexAt(pEvent->pos())); bool draggingOnSelfOrChild = false; if (dropItem) for (int i = 0; (i < indexes.count()) && !draggingOnSelfOrChild; ++i) draggingOnSelfOrChild = itemIsOrIsChildOf(dropItem, mModel->itemFromIndex(indexes[i])); if ( (pEvent->mimeData()->urls().count() || indexes.count()) && ( (dropItem && dropItem->data(Item::Folder).toBool()) || (dropIndicatorPosition() != QAbstractItemView::OnItem)) && !draggingOnSelfOrChild) pEvent->acceptProposedAction(); else pEvent->ignore(); }
void TableViewWidget::dropEvent(QDropEvent *event) { QTableView::dropEvent(event); if (event->isAccepted()) { m_dropRow = indexAt(event->pos()).row(); if (dropIndicatorPosition() == QAbstractItemView::BelowItem) { ++m_dropRow; } emit modified(); QTimer::singleShot(50, this, SLOT(updateDropSelection())); } }
void NTreeView::dropEvent(QDropEvent *event) { QFileSystemModel *model = (QFileSystemModel *)this->model(); // 選択されたファイルのパスを取得 QModelIndex selectedIndex = this->currentIndex(); QString selectedFilePath = model->filePath(selectedIndex); QTreeView::dropEvent(event); // ドロップが無視されたら処理を終了。例えば同じディレクトリなどにドロップした場合は無視される if (!event->isAccepted()) { return; } /* * ドロップされた座標からドロップされた場所のディレクトリパスを取得する. * AbobeItem, BelowItemの場合、ドロップ先はindexAtで取得されたものの親要素となる. * これはもとのQTreeViewのロジックをみて持ってきた. */ QModelIndex dropIndex = QTreeView::indexAt(event->pos()); switch (dropIndicatorPosition()) { case QAbstractItemView::AboveItem: case QAbstractItemView::BelowItem: dropIndex = dropIndex.parent(); break; case QAbstractItemView::OnItem: case QAbstractItemView::OnViewport: break; } QString dropPath; if (dropIndex.isValid()) { if (dropIndex == this->rootIndex()) { dropPath = model->rootPath(); } else { dropPath = model->filePath(dropIndex); } } else { // ドロップがModelIndexの領域外になった場合は、ルートディレクトリへのドロップである dropPath = model->rootPath(); } emit dropped(dropPath, selectedFilePath); }
void ItemViewWidget::dropEvent(QDropEvent *event) { if (m_viewMode == TreeViewMode) { QTreeView::dropEvent(event); return; } QDropEvent mutableEvent(QPointF((visualRect(m_model->index(0, 0)).x() + 1), event->posF().y()), Qt::MoveAction, event->mimeData(), event->mouseButtons(), event->keyboardModifiers(), event->type()); QTreeView::dropEvent(&mutableEvent); if (!mutableEvent.isAccepted()) { return; } event->accept(); m_dropRow = indexAt(event->pos()).row(); if (m_dragRow <= m_dropRow) { --m_dropRow; } if (dropIndicatorPosition() == QAbstractItemView::BelowItem) { ++m_dropRow; } m_isModified = true; emit modified(); QTimer::singleShot(50, this, SLOT(updateDropSelection())); }
void views::treeView::paintEvent(QPaintEvent * event) { QPainter painter(viewport()); drawTree(&painter, event->region()); if(state() ==QAbstractItemView::DraggingState && showDropIndicator() ) { DropIndicatorPosition pos=dropIndicatorPosition (); if(pos==AboveItem) { QModelIndex in=indexAt( viewport()->mapFromGlobal(QCursor::pos() ) ); QRect rect=visualRect(in); rect.setX(viewport()->rect().x() ); rect.setWidth(viewport()->rect().width()); QPen pen(palette().highlight().color() ); pen.setWidth(3); painter.setPen(pen); painter.drawLine(rect.topLeft(),rect.topRight()); } else if(pos==BelowItem) { QModelIndex in=indexAt( viewport()->mapFromGlobal(QCursor::pos() ) ); QRect rect=visualRect(in); rect.setX(viewport()->rect().x() ); rect.setWidth(viewport()->rect().width()); QPen pen(palette().highlight().color() ); pen.setWidth(3); painter.setPen(pen); painter.drawLine(rect.bottomLeft(),rect.bottomRight()); } else if(pos==OnViewport) { if(model()==0) return ; QModelIndex in=model()->index(model()->rowCount()-1,notHide(),QModelIndex() ); while(indexBelow(in).isValid() ) { in=indexBelow(in); } QRect rect=visualRect(in); rect.setX(viewport()->rect().x() ); rect.setWidth(viewport()->rect().width()); QPen pen(palette().highlight().color() ); pen.setWidth(3); painter.setPen(pen); painter.drawLine(rect.bottomLeft(),rect.bottomRight()); } else if(pos==OnItem) { QModelIndex in=indexAt( viewport()->mapFromGlobal(QCursor::pos() ) ); QRect rect=visualRect(in); QPen pen(palette().highlight().color() ); pen.setWidth(2); painter.setPen(pen); painter.drawRect(rect); } } }
void FileOrganiserWidget::dropEvent(QDropEvent *pEvent) { // Note: the MIME data definitely contains the FileSystemMimeType MIME type // (for objects originating from outside this widget), but it may also // contain the FileOrganiserMimeType MIME type (for objects // originating from within this widget). FileOrganiserMimeType is used // by this widget while FileSystemMimeType by external widgets. So, // this means that we must check for FileOrganiserMimeType first // Files have been dropped, so add them to the widget and this at the right // place (i.e. above/on/below a folder, above/below a file or on the // invisible root folder) // First, determine the item above/on/below which objects are to be dropped, // as well as the drop position (i.e. above, on or below) QStandardItem *dropItem; DropIndicatorPosition dropPosition = dropIndicatorPosition(); if (dropPosition == QAbstractItemView::OnViewport) { // We dropped the files on the viewport, so... dropItem = mModel->invisibleRootItem(); // Change the drop position since we know that we want want the objects // to be dropped on the root folder dropPosition = QAbstractItemView::OnItem; } else { // We dropped the files above/on/below a folder or above/below a file, // so... dropItem = mModel->itemFromIndex(indexAt(pEvent->pos())); } // Check the type of MIME data to be dropped if (pEvent->mimeData()->hasFormat(FileOrganiserMimeType)) { // The user is dropping folders/files from ourselves, i.e. s/he wants // some folders/files to be moved around // Retrieve the list of indexes to move around and clean it QByteArray data = pEvent->mimeData()->data(FileOrganiserMimeType); QModelIndexList indexes = cleanIndexList(mModel->decodeData(data)); // Convert our list of indexes to a list of items // Note: indeed, by moving the item corresponding to a particular index, // we may mess up the other indexes, meaning that we may not be // able to retrieve their corresponding item, so... QList<QStandardItem *> items; for (int i = 0, iMax = indexes.count(); i < iMax; ++i) items << mModel->itemFromIndex(indexes[i]); // Move the contents of the list to its final destination if (dropPosition != QAbstractItemView::BelowItem) // Move the items in the order they were dropped for (int i = 0, iMax = items.count(); i < iMax; ++i) moveItem(items[i], dropItem, dropPosition); else // Move the items in a reverse order to that they were dropped since // we want them moved below the current item for (int i = items.count()-1; i >= 0; --i) moveItem(items[i], dropItem, dropPosition); } else { // The user wants to drop files, so add them to the widget and this at // the right place QList<QUrl> urls = pEvent->mimeData()->urls(); if (dropPosition != QAbstractItemView::BelowItem) // Add the files in the order they were dropped for (int i = 0, iMax = urls.count(); i < iMax; ++i) addFile(urls[i].toLocalFile(), dropItem, dropPosition); else // Add the files in a reverse order to that they were dropped since // we want them added below the current item for (int i = urls.count()-1; i >= 0; --i) addFile(urls[i].toLocalFile(), dropItem, dropPosition); } // Accept the proposed action for the event pEvent->acceptProposedAction(); // Reset the state of the widget // Note: there doesn't seem to be and there shouldn't be a need to reset the // state after the widget (the resetting seems to be done elsewhere), // but if don't reset the state of the widget, then the drop indicator // may, in some cases, remain visible (a bug in Qt?), so... setState(QAbstractItemView::NoState); }
void TableView::dropEvent(QDropEvent* e) { // QTreeView::dropEvent(e); DropIndicatorPosition position = dropIndicatorPosition(); switch (position) { case QAbstractItemView::OnItem: case QAbstractItemView::OnViewport: default: return; case QAbstractItemView::AboveItem: case QAbstractItemView::BelowItem: break; } TableItem* into = itemAt( e->pos() ); if ( !into || _imp->draggedItems.empty() ) { return; } Q_EMIT aboutToDrop(); int targetRow = into->row(); //We only support full rows assert(selectionBehavior() == QAbstractItemView::SelectRows); ///Remove the items std::map<int, std::map<int, TableItem*> > rowMoved; for (std::list<TableItem*>::iterator it = _imp->draggedItems.begin(); it != _imp->draggedItems.end(); ++it) { rowMoved[(*it)->row()][(*it)->column()] = *it; TableItem* taken = _imp->model->takeItem( (*it)->row(), (*it)->column() ); assert(taken == *it); Q_UNUSED(taken); } /// remove the rows in reverse order so that indexes are still valid for (std::map<int, std::map<int, TableItem*> >::reverse_iterator it = rowMoved.rbegin(); it != rowMoved.rend(); ++it) { _imp->model->removeRows(it->first); if (it->first <= targetRow) { --targetRow; } } _imp->draggedItems.clear(); ///insert back at the correct position int nRows = _imp->model->rowCount(); switch (position) { case QAbstractItemView::AboveItem: { _imp->model->insertRows( targetRow, rowMoved.size() ); break; } case QAbstractItemView::BelowItem: { ++targetRow; if (targetRow > nRows) { targetRow = nRows; } _imp->model->insertRows( targetRow, rowMoved.size() ); break; } default: assert(false); return; } ; int rowIndex = targetRow; for (std::map<int, std::map<int, TableItem*> >::iterator it = rowMoved.begin(); it != rowMoved.end(); ++it, ++rowIndex) { for (std::map<int, TableItem*>::iterator it2 = it->second.begin(); it2 != it->second.end(); ++it2) { _imp->model->setItem(rowIndex, it2->first, it2->second); } } Q_EMIT itemDropped(); } // TableView::dropEvent
void PlaylistView::paintEvent(QPaintEvent* event) { // Reimplemented to draw the background image. // Reimplemented also to draw the drop indicator // When the user is dragging some stuff over the playlist paintEvent gets // called for the entire viewport every time the user moves the mouse. // The drawTree is kinda expensive, so we cache the result and draw from the // cache while the user is dragging. The cached pixmap gets invalidated in // dragLeaveEvent, dropEvent and scrollContentsBy. // Draw background if (background_image_type_ == Custom || background_image_type_ == AlbumCover) { if (!background_image_.isNull() || !previous_background_image_.isNull()) { QPainter background_painter(viewport()); // Check if we should recompute the background image if (height() != last_height_ || width() != last_width_ || force_background_redraw_) { if (background_image_.isNull()) { cached_scaled_background_image_ = QPixmap(); } else { cached_scaled_background_image_ = QPixmap::fromImage(background_image_.scaled( width(), height(), Qt::KeepAspectRatioByExpanding, Qt::SmoothTransformation)); } last_height_ = height(); last_width_ = width(); force_background_redraw_ = false; } // Actually draw the background image if (!cached_scaled_background_image_.isNull()) { // Set opactiy only if needed, as this deactivate hardware acceleration if (!qFuzzyCompare(previous_background_image_opacity_, qreal(0.0))) { background_painter.setOpacity(1.0 - previous_background_image_opacity_); } background_painter.drawPixmap( (width() - cached_scaled_background_image_.width()) / 2, (height() - cached_scaled_background_image_.height()) / 2, cached_scaled_background_image_); } // Draw the previous background image if we're fading if (!previous_background_image_.isNull()) { background_painter.setOpacity(previous_background_image_opacity_); background_painter.drawPixmap( (width() - previous_background_image_.width()) / 2, (height() - previous_background_image_.height()) / 2, previous_background_image_); } } } QPainter p(viewport()); if (drop_indicator_row_ != -1) { if (cached_tree_.isNull()) { cached_tree_ = QPixmap(size()); cached_tree_.fill(Qt::transparent); QPainter cache_painter(&cached_tree_); drawTree(&cache_painter, event->region()); } p.drawPixmap(0, 0, cached_tree_); } else { drawTree(&p, event->region()); return; } const int first_column = header_->logicalIndex(0); // Find the y position of the drop indicator QModelIndex drop_index = model()->index(drop_indicator_row_, first_column); int drop_pos = -1; switch (dropIndicatorPosition()) { case QAbstractItemView::OnItem: return; // Don't draw anything case QAbstractItemView::AboveItem: drop_pos = visualRect(drop_index).top(); break; case QAbstractItemView::BelowItem: drop_pos = visualRect(drop_index).bottom() + 1; break; case QAbstractItemView::OnViewport: if (model()->rowCount() == 0) drop_pos = 1; else drop_pos = 1 + visualRect(model()->index(model()->rowCount() - 1, first_column)).bottom(); break; } // Draw a nice gradient first QColor line_color(QApplication::palette().color(QPalette::Highlight)); QColor shadow_color(line_color.lighter(140)); QColor shadow_fadeout_color(shadow_color); shadow_color.setAlpha(255); shadow_fadeout_color.setAlpha(0); QLinearGradient gradient(QPoint(0, drop_pos - kDropIndicatorGradientWidth), QPoint(0, drop_pos + kDropIndicatorGradientWidth)); gradient.setColorAt(0.0, shadow_fadeout_color); gradient.setColorAt(0.5, shadow_color); gradient.setColorAt(1.0, shadow_fadeout_color); QPen gradient_pen(QBrush(gradient), kDropIndicatorGradientWidth * 2); p.setPen(gradient_pen); p.drawLine(QPoint(0, drop_pos), QPoint(width(), drop_pos)); // Now draw the line on top QPen line_pen(line_color, kDropIndicatorWidth); p.setPen(line_pen); p.drawLine(QPoint(0, drop_pos), QPoint(width(), drop_pos)); }