PDA

View Full Version : QTreeWidget + drag&drop : How to set pixmap as Icon+Text



pl01
5th April 2011, 16:14
Hi,

During a drag&drop I would like to display the icon and the text of the tree-item in the drag element. How can I do this ?

If I set the pixmap, it only display the icon... but not the text !

Thanks

Added after 28 minutes:

I have a partial solution, like this



void QShaderNavigator::mousePressEvent(QMouseEvent *event)
{
//---- Search for the selected definition
_dragTreeViewItem = itemAt(event->pos());
if (_dragTreeViewItem)
{
QVariant data = _dragTreeViewItem->data(0, 1);
if (data.isNull())
_dragTreeViewItem = 0;
else
{
const QPixmap image = iconShader.pixmap(QSize(16,16));
_dragPainter->drawPixmap(0, 0, 16, 16, image);
_dragPainter->drawText(QRect(20, 0, 170, 20), _dragTreeViewItem->text(0) );
}
}

QTreeWidget::mousePressEvent(event);
}




void QShaderNavigator::mouseMoveEvent(QMouseEvent * event)
{
...
drag->setPixmap( *_dragPixmap );
...
}


But the problem is that I have a big gray background in the Drag item !!!

goldnrod
25th May 2011, 21:20
This post is pretty old, but I'll write this up anyway.

You were on the right track, you just need to paint a transparent rectangle and then use the SourceOver compostion mode of the painter to draw your icon and text over top of the transparent background. The following code differs slightly from yours, but I think you will understand what I'm doing:

///
///
///
void SourceTreeWidget::mousePressEvent(QMouseEvent *event)
{
if ( event->button() == Qt::LeftButton )
{
QTreeWidgetItem * item = itemAt(event->pos());
if ( item && item->childCount() == 0 ) {
startPos = event->pos();
}
else {
startPos.setX(0); startPos.setY(0);
}
}

QTreeWidget::mousePressEvent(event);
}


///
///
///
void SourceTreeWidget::mouseMoveEvent(QMouseEvent *event)
{
if ( (event->buttons() & Qt::LeftButton) && !startPos.isNull() )
{
int distance = (event->pos() - startPos).manhattanLength();
if (distance >= QApplication::startDragDistance())
{
QTreeWidgetItem * dragTreeViewItem = itemAt(startPos);

//
// Paint an image composed of a transparent background and an icon and some text
//
QImage icon(QString(":/images/bean.ico"));
QSize dragImageSize(186, 20);
QImage dragImage(dragImageSize, QImage::Format_ARGB32_Premultiplied);

QPainter dragPainter(&dragImage);

dragPainter.setCompositionMode(QPainter::Compositi onMode_Source);
dragPainter.fillRect(dragImage.rect(), Qt::transparent);

dragPainter.setCompositionMode(QPainter::Compositi onMode_SourceOver);
dragPainter.drawPixmap(0, 0, 16, 16, QPixmap::fromImage(icon));
dragPainter.drawText(QRect(20, 0, 170, 20), dragTreeViewItem->text(0) );

dragPainter.end();

QDrag *drag = new QDrag(this);
drag->setPixmap( QPixmap::fromImage(dragImage) );


QMimeData *mimeData = new QMimeData;
mimeData->setText(dragTreeViewItem->text(0));
drag->setMimeData(mimeData);
drag->exec(Qt::MoveAction);
}
}

QTreeWidget::mouseMoveEvent(event);
}


I had to do the same thing for a project, but with multi-select. I'm attaching a project (treeMultiDrag.zip) that shows how to do the same thing with more elaborate multi-select.