Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Expensive operation on Drag and Drop
Forum Updated to NodeBB v4.3 + New Features

Expensive operation on Drag and Drop

Scheduled Pinned Locked Moved General and Desktop
6 Posts 4 Posters 1.9k Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • N Offline
    N Offline
    nerdy_weirdie
    wrote on last edited by
    #1

    Hi, I have a desktop operation written on C++/Qt.
    When Items are being dragged from my Application's main window to some other application I need to perform an expensive time consuming operation on these items (decrypt the data of those items).
    I implemented these operations in the mouseMoveEvent, and the application window becomes blocked rignt whed the dragging starts.

    What I want to do is to perform these operations when the dragging is finished, i.e. when the user releases the mouse button above some other application's window.
    But seems like this is not really possible because I need to finish decrypting data to call drag->setMimeData() before the dragging starts.

    1 Reply Last reply
    0
    • S Offline
      S Offline
      Soraltan
      wrote on last edited by
      #2

      Hi,

      welcome. So the problem, that GUI operations can trigger computations, which block the Qt Event queue for long enough to make the window freeze is a general one to which the most basic answer is of cause threading.

      In Qt threading is not as enervating and error prone as you might be used to (see "here":http://qt-project.org/doc/qt-4.8/threads-qobject.html for details). The general idea is that any QObject has an owning QThread. Each QThread runs an event queue. So when you have a GUI operation that triggers a costly operation, I would

      write a QObject subclass that performs this operation within a slot

      then make an instance of it

      make a QThread instance and call start on it

      "move":http://qt-project.org/doc/qt-4.8/qobject.html#moveToThread the computation object to the thread

      connect the gui signal of the triggering gui operation to a slot of your computation object, which starts the computation. This connection will be a "QueuedConnection":http://qt-project.org/doc/qt-5/qt.html#ConnectionType-enum automatically.

      However packing the results into a MimeData and sending it is a differnt issue. I must admit that I never actually used Mime data. Maybe somene else can help here?!?

      Best Soraltan

      1 Reply Last reply
      0
      • N Offline
        N Offline
        nerdy_weirdie
        wrote on last edited by
        #3

        Thank you for your answer, Soraltan!

        The problem is that the current implementation of QDrag class requires that the data decryption finishes before dragging actually starts because it require calling QDrag::setMimeData() which should accept decrypted into the temporary directory file paths as an argument.
        Therefore the GUI thread still needs to wait until the operation completes and there will be a huge lag between the user's attempt to drag an item and the Application's reaction to it even if using threads.

        1. How can I start dragging without knowing the paths of decrypted files?
        2. How can I get notified about the dragging has finished and supply decrypted file paths to the application that accepted the drag at this moment?
        1 Reply Last reply
        0
        • SGaistS Offline
          SGaistS Offline
          SGaist
          Lifetime Qt Champion
          wrote on last edited by
          #4

          Hi,

          One example might interest you: Delayed Encoding in the Drag and Drop examples in Qt's documentation.

          Hope it helps

          Interested in AI ? www.idiap.ch
          Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

          1 Reply Last reply
          0
          • N Offline
            N Offline
            nerdy_weirdie
            wrote on last edited by
            #5

            SGaist,
            Sounds promising, thanks a lot! I'll check this article!

            1 Reply Last reply
            0
            • A Offline
              A Offline
              adolby
              wrote on last edited by
              #6

              The example SGaist linked is a great way to accomplish this, and likely the best solution. I was writing some sample code up before I saw that example, so I thought I'd post it for you anyways:

              Widget.hpp

              @
              #include "Decryptor.hpp"

              #include <QtWidgets/QWidget>
              #include <QtGui/QDrag>

              class Widget : public QWidget
              {
              Q_OBJECT

              public:
              explicit Widget(QWidget* parent = NULL);
              virtual ~Widget();

              signals:
              void doDecrypt(const QString& text, QDrag* drag);

              public slots:
              void processDragRequest(const QString& plainText, QDrag* drag);

              protected:
              void mousePressEvent(QMouseEvent* event);

              private:
              Decryptor* decrypt;
              };
              @

              Widget.cpp

              @
              #include "Widget.hpp"

              #include <QtCore/QThread>
              #include <QtCore/QMimeData>
              #include <QtGui/QMouseEvent>

              Widget::Widget(QWidget* parent) :
              QWidget(parent),
              {
              decrypt = new Decryptor();

              QThread* decryptThread = new QThread(this);
              decrypt->moveToThread(decryptThread);

              connect(this, &Widget::doDecrypt, decrypt, &Decryptor::doDecrypt);
              connect(decrypt, &Decryptor::doneDecrypt, this, &Widget::processDragRequest);

              decryptThread->start();
              }

              void Widget::processDragRequest(const QString& plainText, QDrag* drag)
              {
              Qt::DropAction dropAction = drag->exec(Qt::CopyAction | Qt::MoveAction, Qt::CopyAction);
              }

              void Widget::mousePressEvent(QMouseEvent* event)
              {
              // Get your cipher text
              QString cipherText;

              QMimeData* mimeData = new QMimeData();
              mimeData->setText(cipherText);

              QDrag* drag = new QDrag(this);
              drag->setMimeData(mimeData);

              emit doDecrypt(cipherText, drag);
              }
              @

              Decryptor.hpp
              @
              #include <QtCore/QObject>
              #include <QtGui/QDrag>

              class Decryptor : public QObject
              {
              Q_OBJECT

              public:
              explicit Decryptor(QObject* parent = NULL);

              signals:
              void doneDecrypt(const QString& plainText, QDrag* drag);

              public slots:
              void doDecrypt(const QString& cipherText, QDrag* drag);
              };
              @

              Decryptor.cpp

              @#include "decryptor.hpp"

              #include <QtCore/QDebug>

              Decryptor::Decryptor(QObject* parent) :
              QObject(parent)
              {}

              void Decryptor::doDecrypt(const QString& cipherText, QDrag* drag)
              {
              for (int i = 0; i < 100000; ++i)
              {
              qDebug() << i;
              }

              QString decryptedText = "decryptedText";

              emit doneDecrypt(plainText, drag);
              }
              @

              1 Reply Last reply
              0

              • Login

              • Login or register to search.
              • First post
                Last post
              0
              • Categories
              • Recent
              • Tags
              • Popular
              • Users
              • Groups
              • Search
              • Get Qt Extensions
              • Unsolved