Page 1 of 2 12 LastLast
Results 1 to 20 of 22

Thread: Drag & Drop using QTableWidget

Hybrid View

Previous Post Previous Post   Next Post Next Post
  1. #1
    Join Date
    Feb 2007
    Posts
    7
    Qt products
    Qt4
    Platforms
    Unix/X11

    Default Drag & Drop using QTableWidget

    I'm trying to implement Drag & Drop using a QTableWidget and I haven't been having much luck. I've been trying to get a hold of the QTableWidgetItem that the cursor is over using the itemAt(int x, int y) function using the QMouseEvent event but I keep getting a NULL pointer.

    Qt Code:
    1. void table_widget::mousePressEvent(QMouseEvent *event) {
    2. QMenu *popupMenu = new QMenu(this);
    3. popupMenu->addAction("Drag");
    4. popupMenu->addAction("Drop");
    5.  
    6. if (event->button() == Qt::RightButton) {
    7. popupMenu->popup(QPoint(event->x()+216,event->y()+130), 0);
    8. printf("%x\n",itemAt(event->x()+216,event->y()+130));
    9. }
    10. }
    To copy to clipboard, switch view to plain text mode 

    The 216 and 130 are just offsets from the top left corner of the GUI to the top left corner of the first cell in the table.

    Any suggestions?

  2. #2
    Join Date
    Feb 2006
    Location
    Oslo, Norway
    Posts
    6,264
    Thanks
    36
    Thanked 1,519 Times in 1,389 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows Symbian S60 Maemo/MeeGo

    Default Re: Drag & Drop using QTableWidget

    For drag and drop, take a look at Using Drag and Drop with Item Views - Using Convenience Views.

    For context menu, you might want to reimplement contextMenuEvent() instead. More or less something like this:
    Qt Code:
    1. void table_widget::contextMenuEvent(QContextMenuEvent *event) {
    2. QMenu popupMenu(this);
    3. popupMenu.addAction(...);
    4. popupMenu.exec(event->globalPos());
    5. }
    To copy to clipboard, switch view to plain text mode 
    J-P Nurmi

  3. #3
    Join Date
    Feb 2007
    Posts
    7
    Qt products
    Qt4
    Platforms
    Unix/X11

    Default Re: Drag & Drop using QTableWidget

    I fixed that problem, I just had to create a new QTableWidgetItem for each cell in the table.
    I did have another question though, for dropEvent, it doesnt seem like the function is being called. I have it set up so that it prints a message when it enters that function but the message is never displayed. What could be wrong?
    Here's the code for that function:

    Qt Code:
    1. void table_widget::dropEvent(QDropEvent *event)
    2. {
    3. printf("dropEvent\n");
    4. event->acceptProposedAction();
    5. }
    To copy to clipboard, switch view to plain text mode 

    I even tried inserting if (event->mimeData()->hasText()) before the printf() statement but that doesnt really do anything.

  4. #4
    Join Date
    Jan 2006
    Location
    Paris, France
    Posts
    227
    Thanks
    3
    Thanked 21 Times in 21 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows

    Default Re: Drag & Drop using QTableWidget

    Hello,

    You have to do those two steps :

    1 - call setAcceptDrops(true) on your tablewidget
    2 - reimplement dragEnterEvent method, and accept it !

    I'm not sure if the second step is absolutely necessary for a tablewidget, but the first is, for sure

    Guilugi

  5. #5
    Join Date
    Feb 2007
    Posts
    7
    Qt products
    Qt4
    Platforms
    Unix/X11

    Default Re: Drag & Drop using QTableWidget

    I just had to reimplement dragMoveEvent() and it worked fine, thanks.

    Now I'm having another 'problem'. In my project I'm trying to drag and drop from one QTableWidget to another but I can't quite get it right. The dragEnterEvent acknowledges when I've entered another QTableWidget but thats about it. Here's what I'm working with:

    Qt Code:
    1. void table_widget::dragEnterEvent(QDragEnterEvent *event)
    2. {
    3. QTableWidgetItem* test = itemAt(event->pos());
    4. if (test != 0)
    5. {
    6. if ( event->source() == this ) // same table, move entry
    7. {
    8. event->setDropAction( Qt::MoveAction );
    9. event->accept();
    10. }
    11. else // different table, add entry
    12. {
    13. printf("Different table\n");
    14. event->acceptProposedAction();
    15. }
    16.  
    17. source = itemAt(event->pos());
    18. source->setText(itemAt(event->pos())->text());
    19. }
    20. }
    21.  
    22. void table_widget::dropEvent(QDropEvent *event)
    23. {
    24. printf("I'm in dropEvent\n");
    25. itemAt(event->pos())->setText(source->text());
    26. if(source != itemAt(event->pos()))
    27. source->setText("");
    28. event->acceptProposedAction();
    29. }
    30.  
    31. void table_widget::dragMoveEvent(QDragMoveEvent *event)
    32. {
    33. event->setDropAction(Qt::MoveAction);
    34. event->accept();
    35. }
    To copy to clipboard, switch view to plain text mode 

    Any suggestions?
    Last edited by Israa; 3rd March 2007 at 21:30.

  6. #6
    Join Date
    Nov 2006
    Location
    Dresden, Germany
    Posts
    108
    Thanks
    9
    Thanked 12 Times in 10 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows

    Default Re: Drag & Drop using QTableWidget

    I have exactly the same problem. I called set setAcceptDrops(true) and reimplemented dragEnterEvent(QDragEnterEvent *event), which gets called and I accept the proposed copy-action.

    However, my reimplemented dropEvent function is never called. The documentation and examples say it will be called, but I couldn't get this to work :-(

    Btw, this is Qt Open Source 4.2.2.

    Any suggestions?

  7. #7
    Join Date
    Nov 2006
    Location
    Dresden, Germany
    Posts
    108
    Thanks
    9
    Thanked 12 Times in 10 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows

    Exclamation Re: Drag & Drop using QTableWidget

    Correction to my last post: It is Qt Open Source 4.2.1

    I believe I have found the problem. In qtablewidget.h, in the class declaration for QTableWidget the function dropEvent() is not declared as virtual, thus our reimplemented dropEvent() function will never be called.

    I guess I have to check with 4.2.2 and see if this was fixed...

    Andreas

  8. #8
    Join Date
    Feb 2006
    Location
    Oslo, Norway
    Posts
    6,264
    Thanks
    36
    Thanked 1,519 Times in 1,389 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows Symbian S60 Maemo/MeeGo

    Default Re: Drag & Drop using QTableWidget

    Quote Originally Posted by ghorwin View Post
    I believe I have found the problem. In qtablewidget.h, in the class declaration for QTableWidget the function dropEvent() is not declared as virtual, thus our reimplemented dropEvent() function will never be called.
    It's declared virtual in QWidget.
    http://www.qtcentre.org/forum/p-reim...ostcount5.html
    J-P Nurmi

  9. #9
    Join Date
    Nov 2006
    Location
    Dresden, Germany
    Posts
    108
    Thanks
    9
    Thanked 12 Times in 10 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows

    Default Re: Drag & Drop using QTableWidget

    Yes, that's why it works when you inherit from QTableView... however, QTableWidget provides its own implementation of dropEvent() without declaring it virtual. Therefore classes deriving from QTableWidget will not be able to reimplement that function, or if they do the function will never get called.

    Andreas

  10. #10
    Join Date
    Feb 2006
    Location
    Oslo, Norway
    Posts
    6,264
    Thanks
    36
    Thanked 1,519 Times in 1,389 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows Symbian S60 Maemo/MeeGo

    Default Re: Drag & Drop using QTableWidget

    Actually, it doesn't matter if QTableWidget marks it virtual or not. It has already been declared as virtual in the base class, in QWidget that is.
    Quote Originally Posted by jacek View Post
    Once a method was declared as virtual, it will be virtual in all subclasses, regardless if one uses the "virtual" keyword or not.
    J-P Nurmi

  11. #11
    Join Date
    Nov 2006
    Location
    Dresden, Germany
    Posts
    108
    Thanks
    9
    Thanked 12 Times in 10 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows

    Unhappy Re: Drag & Drop using QTableWidget

    jpn: I have to agree. The problem must lie elsewhere.

    A test-implementation using QTableView showed the same behavior - the dragEnterEvent() is called correctly but despite the fact, that acceptProposedAction() is called, the reimplemented dropEvent() function is never called.

    Did anyone manage to implement drag&drop with QTableView or QTableWidget already? What is missing to get this to work?

    Andreas
    Andreas

  12. #12
    Join Date
    Feb 2006
    Location
    Oslo, Norway
    Posts
    6,264
    Thanks
    36
    Thanked 1,519 Times in 1,389 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows Symbian S60 Maemo/MeeGo

    Default Re: Drag & Drop using QTableWidget

    Quote Originally Posted by ghorwin View Post
    A test-implementation using QTableView showed the same behavior - the dragEnterEvent() is called correctly but despite the fact, that acceptProposedAction() is called, the reimplemented dropEvent() function is never called.
    Is the drag move event accepted?
    J-P Nurmi

  13. #13
    Join Date
    Feb 2007
    Posts
    7
    Qt products
    Qt4
    Platforms
    Unix/X11

    Default Re: Drag & Drop using QTableWidget

    Bump. ghorwin 'hijacked' my thread!

  14. #14
    Join Date
    Nov 2006
    Location
    Dresden, Germany
    Posts
    108
    Thanks
    9
    Thanked 12 Times in 10 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows

    Question Re: Drag & Drop using QTableWidget

    Israa: Sorry for hijacking, but you asked excactly the same question that I had, so figured opening a new thread would be non-sense.

    Jpn: dragMoveEvent() is called correctly.

    So it seems something prevents the dropping...

    If I read the documentation correctly, only the widget itself, that should accept the drop, needs to call setAcceptDrop(), right? Or do I also have to tell the parent dialog to accept drops?

    Anyway, I'm clueless. Should I post a simple test-program?
    Andreas

  15. #15
    Join Date
    Feb 2006
    Location
    Oslo, Norway
    Posts
    6,264
    Thanks
    36
    Thanked 1,519 Times in 1,389 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows Symbian S60 Maemo/MeeGo

    Default Re: Drag & Drop using QTableWidget

    Quote Originally Posted by ghorwin View Post
    Jpn: dragMoveEvent() is called correctly.
    Yes, but do you accept the event?
    J-P Nurmi

  16. #16
    Join Date
    Nov 2006
    Location
    Dresden, Germany
    Posts
    108
    Thanks
    9
    Thanked 12 Times in 10 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows

    Thumbs up Re: Drag & Drop using QTableWidget

    Guys, got it to work!!!

    The trick is to call
    Qt Code:
    1. setDragDropMode(QAbstractItemView::DropOnly);
    To copy to clipboard, switch view to plain text mode 
    in addition to
    Qt Code:
    1. setAcceptDrops(true);
    To copy to clipboard, switch view to plain text mode 
    (wasn't mentioned in the docu, but I just went back to the abstract view class)...

    Now dropEvent is called alright!
    Andreas

  17. #17
    Join Date
    Nov 2006
    Location
    Dresden, Germany
    Posts
    108
    Thanks
    9
    Thanked 12 Times in 10 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows

    Default Re: Drag & Drop using QTableWidget

    Still something strange about the dropping...

    Explain that: When I reimplement the dragMoveEvent() (even with an empty function), I can drop anywhere in my table. If I don't reimplement it, I can only drop when the cursor is exactly on the frame around the content rows (so at the bottom of the header row and at the top of the horizontal scroll bar). That's weird, if you ask me.

    So, the recipe for dropping on QTableWidget is:

    1. setup your table in the constructor
    Qt Code:
    1. setDragDropMode(QAbstractItemView::DropOnly);
    2. setAcceptDrops(true);
    To copy to clipboard, switch view to plain text mode 

    2. re-implement the functions dragEnterEvent(...), dragMoveEvent(...) and dropEvent(...), for example:
    Qt Code:
    1. void MyTable::dragEnterEvent(QDragEnterEvent *event)
    2. {
    3. if (event->mimeData()->hasUrls()) {
    4. event->acceptProposedAction();
    5. }
    6. }
    7.  
    8. void MyTable::dragMoveEvent ( QDragMoveEvent * ) {
    9. // nothing to do, function just has to exist...
    10. }
    11.  
    12. void MyTable::dropEvent(QDropEvent *event)
    13. {
    14. if (event->mimeData()->hasUrls()) {
    15. QList<QUrl> urls = event->mimeData()->urls();
    16. for (int i=0; i<urls.count(); ++i) {
    17. int row = rowCount();
    18. insertRow(row);
    19. QTableWidgetItem *newItem = new QTableWidgetItem(urls[i].toString());
    20. setItem(row, 0, newItem);
    21. }
    22.  
    23. event->accept();
    24. }
    25. }
    To copy to clipboard, switch view to plain text mode 
    At least that's what worked for me.
    Andreas

  18. #18
    Join Date
    Feb 2007
    Posts
    7
    Qt products
    Qt4
    Platforms
    Unix/X11

    Default Re: Drag & Drop using QTableWidget

    I still haven't gotten an answer to my question, would anyone know what I need to do to enable drag & drop to and from 2 QTableWidgets? I create a class that inherits QTableWidget and I place the two objects on either side of a QSplitter. I can drag & drop in the same table, but not to the other table.

  19. #19
    Join Date
    Feb 2006
    Location
    Oslo, Norway
    Posts
    6,264
    Thanks
    36
    Thanked 1,519 Times in 1,389 Posts
    Qt products
    Qt4
    Platforms
    MacOS X Unix/X11 Windows Symbian S60 Maemo/MeeGo

    Default Re: Drag & Drop using QTableWidget

    Using Drag and Drop with Item Views - Using Convenience Views:
    For example, we can enable drag and drop in a list widget with the following lines of code:

    Qt Code:
    1. QListWidget *listWidget = new QListWidget(this);
    2. listWidget->setSelectionMode(QAbstractItemView::SingleSelection);
    3. listWidget->setDragEnabled(true);
    4. listWidget->setAcceptDrops(true);
    5. listWidget->setDropIndicatorShown(true);
    To copy to clipboard, switch view to plain text mode 
    The same applies for a table widget.
    J-P Nurmi

  20. #20
    Join Date
    Oct 2006
    Posts
    5
    Qt products
    Qt4

    Default Re: Drag & Drop using QTableWidget

    Quote Originally Posted by Israa View Post
    I still haven't gotten an answer to my question, would anyone know what I need to do to enable drag & drop to and from 2 QTableWidgets? I create a class that inherits QTableWidget and I place the two objects on either side of a QSplitter. I can drag & drop in the same table, but not to the other table.
    I am having the same problem, trying to drag&drop from one table to another.

    Quote Originally Posted by jpn View Post
    I am having trouble following the page you linked. I have tried the function calls that enable drag&drop functionality, but I am still having issues dropping to a different table than was dragged from. Is there any way some short example code could be provided? Nothing complicated, I'd just like to see a working example.

    Thanks.

Similar Threads

  1. Drag & drop with model/view (Qt4)
    By yogeshm02 in forum Qt Programming
    Replies: 16
    Last Post: 19th September 2011, 21:36
  2. Drag and Drop
    By allensr in forum Qt Programming
    Replies: 1
    Last Post: 11th December 2006, 21:50
  3. Replies: 7
    Last Post: 8th September 2006, 17:19
  4. Drag and drop revisited
    By Big Duck in forum Newbie
    Replies: 2
    Last Post: 30th June 2006, 17:41
  5. Drag 'n Drop problem
    By kiker99 in forum Qt Programming
    Replies: 4
    Last Post: 16th January 2006, 17:35

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  
Digia, Qt and their respective logos are trademarks of Digia Plc in Finland and/or other countries worldwide.