Qt 4.8
qdnd_x11.cpp
Go to the documentation of this file.
1 /****************************************************************************
2 **
3 ** Copyright (C) 2014 Digia Plc and/or its subsidiary(-ies).
4 ** Contact: http://www.qt-project.org/legal
5 **
6 ** This file is part of the QtGui module of the Qt Toolkit.
7 **
8 ** $QT_BEGIN_LICENSE:LGPL$
9 ** Commercial License Usage
10 ** Licensees holding valid commercial Qt licenses may use this file in
11 ** accordance with the commercial license agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and Digia. For licensing terms and
14 ** conditions see http://qt.digia.com/licensing. For further information
15 ** use the contact form at http://qt.digia.com/contact-us.
16 **
17 ** GNU Lesser General Public License Usage
18 ** Alternatively, this file may be used under the terms of the GNU Lesser
19 ** General Public License version 2.1 as published by the Free Software
20 ** Foundation and appearing in the file LICENSE.LGPL included in the
21 ** packaging of this file. Please review the following information to
22 ** ensure the GNU Lesser General Public License version 2.1 requirements
23 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
24 **
25 ** In addition, as a special exception, Digia gives you certain additional
26 ** rights. These rights are described in the Digia Qt LGPL Exception
27 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
28 **
29 ** GNU General Public License Usage
30 ** Alternatively, this file may be used under the terms of the GNU
31 ** General Public License version 3.0 as published by the Free Software
32 ** Foundation and appearing in the file LICENSE.GPL included in the
33 ** packaging of this file. Please review the following information to
34 ** ensure the GNU General Public License version 3.0 requirements will be
35 ** met: http://www.gnu.org/copyleft/gpl.html.
36 **
37 **
38 ** $QT_END_LICENSE$
39 **
40 ****************************************************************************/
41 
42 #include "qplatformdefs.h"
43 
44 #include "qapplication.h"
46 
47 #ifndef QT_NO_DRAGANDDROP
48 
49 #include "qwidget.h"
50 #include "qpainter.h"
51 #include "qpixmap.h"
52 #include "qbitmap.h"
53 #include "qdesktopwidget.h"
54 #include "qevent.h"
55 #include "qiodevice.h"
56 #include "qpointer.h"
57 #include "qcursor.h"
58 #include "qelapsedtimer.h"
59 #include "qvariant.h"
60 #include "qvector.h"
61 #include "qurl.h"
62 #include "qdebug.h"
63 #include "qimagewriter.h"
64 #include "qbuffer.h"
65 #include "qtextcodec.h"
66 
67 #include "qdnd_p.h"
68 #include "qapplication_p.h"
69 #include "qt_x11_p.h"
70 #include "qx11info_x11.h"
71 
72 #include "qwidget_p.h"
73 #include "qcursor_p.h"
74 
75 #ifndef QT_NO_XFIXES
76 #include <X11/extensions/Xfixes.h>
77 #endif
78 
80 
81 // #define DND_DEBUG
82 #ifdef DND_DEBUG
83 #define DEBUG qDebug
84 #else
85 #define DEBUG if(0) qDebug
86 #endif
87 
88 #ifdef DND_DEBUG
89 #define DNDDEBUG qDebug()
90 #else
91 #define DNDDEBUG if(0) qDebug()
92 #endif
93 
95 {
96  int at = -1;
97  for (int i = 0; i < X11->dndDropTransactions.count(); ++i) {
98  const QXdndDropTransaction &t = X11->dndDropTransactions.at(i);
99  if (t.target == window || t.proxy_target == window) {
100  at = i;
101  break;
102  }
103  }
104  return at;
105 }
106 
107 static int findXdndDropTransactionByTime(Time timestamp)
108 {
109  int at = -1;
110  for (int i = 0; i < X11->dndDropTransactions.count(); ++i) {
111  const QXdndDropTransaction &t = X11->dndDropTransactions.at(i);
112  if (t.timestamp == timestamp) {
113  at = i;
114  break;
115  }
116  }
117  return at;
118 }
119 
120 // timer used to discard old XdndDrop transactions
121 static int transaction_expiry_timer = -1;
122 enum { XdndDropTransactionTimeout = 5000 }; // 5 seconds
123 
125 {
126  if (transaction_expiry_timer != -1)
129 }
130 
131 
132 // find an ancestor with XdndAware on it
134 {
135  Window target = 0;
136  forever {
137  // check if window has XdndAware
138  Atom type = 0;
139  int f;
140  unsigned long n, a;
141  unsigned char *data = 0;
142  if (XGetWindowProperty(X11->display, window, ATOM(XdndAware), 0, 0, False,
143  AnyPropertyType, &type, &f,&n,&a,&data) == Success) {
144  if (data)
145  XFree(data);
146  if (type) {
147  target = window;
148  break;
149  }
150  }
151 
152  // try window's parent
153  Window root;
154  Window parent;
155  Window *children;
156  uint unused;
157  if (!XQueryTree(X11->display, window, &root, &parent, &children, &unused))
158  break;
159  if (children)
160  XFree(children);
161  if (window == root)
162  break;
163  window = parent;
164  }
165  return target;
166 }
167 
168 
169 
170 
171 // and all this stuff is copied -into- qapp_x11.cpp
172 
173 static void handle_xdnd_position(QWidget *, const XEvent *, bool);
174 static void handle_xdnd_status(QWidget * w, const XEvent * xe, bool /*passive*/);
175 
176 const int xdnd_version = 5;
177 
179 {
180  if (atom == ATOM(XdndActionCopy) || atom == 0)
181  return Qt::CopyAction;
182  if (atom == ATOM(XdndActionLink))
183  return Qt::LinkAction;
184  if (atom == ATOM(XdndActionMove))
185  return Qt::MoveAction;
186  return Qt::CopyAction;
187 }
188 
190 {
191  switch (a) {
192  case Qt::CopyAction:
193  return ATOM(XdndActionCopy);
194  case Qt::LinkAction:
195  return ATOM(XdndActionLink);
196  case Qt::MoveAction:
198  return ATOM(XdndActionMove);
199  case Qt::IgnoreAction:
200  return XNone;
201  default:
202  return ATOM(XdndActionCopy);
203  }
204 }
205 
206 // clean up the stuff used.
207 static void qt_xdnd_cleanup();
208 
209 static void qt_xdnd_send_leave();
210 
211 // real variables:
212 // xid of current drag source
214 
215 // the types in this drop. 100 is no good, but at least it's big.
216 const int qt_xdnd_max_type = 100;
218 
219 // timer used when target wants "continuous" move messages (eg. scroll)
220 static int heartbeat = -1;
221 // rectangle in which the answer will be the same
223 // top-level window we sent position to last.
225 // window to send events to (always valid if qt_xdnd_current_target)
228 
229 // widget we forwarded position to last, and local position
232 // timestamp from the XdndPosition and XdndDrop
234 // screen number containing the pointer... -1 means default
235 static int qt_xdnd_current_screen = -1;
236 // state of dragging... true if dragging, false if not
237 bool qt_xdnd_dragging = false;
238 
239 static bool waiting_for_status = false;
240 
241 // used to preset each new QDragMoveEvent
243 
244 // Shift/Ctrl handling, and final drop status
246 static Qt::DropActions possible_actions = Qt::IgnoreAction;
247 
248 // for embedding only
251 
252 // cursors
253 static QCursor *noDropCursor = 0;
254 static QCursor *moveCursor = 0;
255 static QCursor *copyCursor = 0;
256 static QCursor *linkCursor = 0;
257 
258 static QPixmap *defaultPm = 0;
259 
260 static const int default_pm_hotx = -2;
261 static const int default_pm_hoty = -16;
262 static const char* const default_pm[] = {
263 "13 9 3 1",
264 ". c None",
265 " c #000000",
266 "X c #FFFFFF",
267 "X X X X X X X",
268 " X X X X X X ",
269 "X ......... X",
270 " X.........X ",
271 "X ......... X",
272 " X.........X ",
273 "X ......... X",
274 " X X X X X X ",
275 "X X X X X X X"
276 };
277 
278 class QShapedPixmapWidget : public QWidget
279 {
280  Q_OBJECT
281 public:
283  QWidget(w,
287  {
289  }
290 
291  void setPixmap(const QPixmap &pm)
292  {
293  QBitmap mask = pm.mask();
294  if (!mask.isNull()) {
295  setMask(mask);
296  } else {
297  clearMask();
298  }
299  resize(pm.width(),pm.height());
300  pixmap = pm;
301  update();
302  }
304 
305 protected:
306  QPixmap pixmap;
308  {
309  QPainter p(this);
310  p.drawPixmap(0, 0, pixmap);
311  }
312 };
313 
314 #include "qdnd_x11.moc"
315 
316 struct XdndData {
319 };
320 
321 static XdndData xdnd_data = { 0, 0 };
322 
323 class QExtraWidget : public QWidget
324 {
326 public:
327  inline QWExtra* extraData();
328  inline QTLWExtra* topData();
329 };
330 
331 inline QWExtra* QExtraWidget::extraData() { return d_func()->extraData(); }
332 inline QTLWExtra* QExtraWidget::topData() { return d_func()->topData(); }
333 
334 
335 static WId xdndProxy(WId w)
336 {
337  Atom type = XNone;
338  int f;
339  unsigned long n, a;
340  unsigned char *retval = 0;
341  XGetWindowProperty(X11->display, w, ATOM(XdndProxy), 0, 1, False,
342  XA_WINDOW, &type, &f,&n,&a,&retval);
343  WId *proxy_id_ptr = (WId *)retval;
344  WId proxy_id = 0;
345  if (type == XA_WINDOW && proxy_id_ptr) {
346  proxy_id = *proxy_id_ptr;
347  XFree(proxy_id_ptr);
348  proxy_id_ptr = 0;
349  // Already exists. Real?
350  X11->ignoreBadwindow();
351  XGetWindowProperty(X11->display, proxy_id, ATOM(XdndProxy), 0, 1, False,
352  XA_WINDOW, &type, &f,&n,&a,&retval);
353  proxy_id_ptr = (WId *)retval;
354  if (X11->badwindow() || type != XA_WINDOW || !proxy_id_ptr || *proxy_id_ptr != proxy_id)
355  // Bogus - we will overwrite.
356  proxy_id = 0;
357  }
358  if (proxy_id_ptr)
359  XFree(proxy_id_ptr);
360  return proxy_id;
361 }
362 
363 static bool xdndEnable(QWidget* w, bool on)
364 {
365  DNDDEBUG << "xdndEnable" << w << on;
366  if (on) {
367  QWidget * xdnd_widget = 0;
368  if ((w->windowType() == Qt::Desktop)) {
369  if (xdnd_data.desktop_proxy) // *WE* already have one.
370  return false;
371 
372  // As per Xdnd4, use XdndProxy
373  XGrabServer(X11->display);
375  WId proxy_id = xdndProxy(w->effectiveWinId());
376 
377  if (!proxy_id) {
378  xdnd_widget = xdnd_data.desktop_proxy = new QWidget;
379  proxy_id = xdnd_data.desktop_proxy->effectiveWinId();
380  XChangeProperty (X11->display, w->effectiveWinId(), ATOM(XdndProxy),
381  XA_WINDOW, 32, PropModeReplace, (unsigned char *)&proxy_id, 1);
382  XChangeProperty (X11->display, proxy_id, ATOM(XdndProxy),
383  XA_WINDOW, 32, PropModeReplace, (unsigned char *)&proxy_id, 1);
384  }
385 
386  XUngrabServer(X11->display);
387  } else {
388  xdnd_widget = w->window();
389  }
390  if (xdnd_widget) {
391  DNDDEBUG << "setting XdndAware for" << xdnd_widget << xdnd_widget->effectiveWinId();
392  Atom atm = (Atom)xdnd_version;
394  XChangeProperty(X11->display, xdnd_widget->effectiveWinId(), ATOM(XdndAware),
395  XA_ATOM, 32, PropModeReplace, (unsigned char *)&atm, 1);
396  return true;
397  } else {
398  return false;
399  }
400  } else {
401  if ((w->windowType() == Qt::Desktop)) {
402  XDeleteProperty(X11->display, w->internalWinId(), ATOM(XdndProxy));
403  delete xdnd_data.desktop_proxy;
404  xdnd_data.desktop_proxy = 0;
405  } else {
406  DNDDEBUG << "not deleting XDndAware";
407  }
408  return true;
409  }
410 }
411 
413 {
414  if (!a) return 0;
415 
416  if (a == XA_STRING || a == ATOM(UTF8_STRING)) {
417  return "text/plain"; // some Xdnd clients are dumb
418  }
419  char *atom = XGetAtomName(display, a);
420  QByteArray result = atom;
421  XFree(atom);
422  return result;
423 }
424 
425 Atom QX11Data::xdndStringToAtom(const char *mimeType)
426 {
427  if (!mimeType || !*mimeType)
428  return 0;
429  return XInternAtom(display, mimeType, False);
430 }
431 
432 //$$$
434 {
435  QString atomName;
436  if (a) {
437  char *atom = XGetAtomName(display, a);
438  atomName = QString::fromLatin1(atom);
439  XFree(atom);
440  }
441  return atomName;
442 }
443 
444 //$$$
446 {
447  if (mimeType.isEmpty())
448  return 0;
449  return XInternAtom(display, mimeType.toLatin1().constData(), False);
450 }
451 
452 //$$$ replace ccxdndAtomToString()
454 {
455  QStringList formats;
456  if (a) {
457  QString atomName = xdndMimeAtomToString(a);
458  formats.append(atomName);
459 
460  // special cases for string type
461  if (a == ATOM(UTF8_STRING) || a == XA_STRING
462  || a == ATOM(TEXT) || a == ATOM(COMPOUND_TEXT))
463  formats.append(QLatin1String("text/plain"));
464 
465  // special cases for uris
466  if (atomName == QLatin1String("text/x-moz-url"))
467  formats.append(QLatin1String("text/uri-list"));
468 
469  // special case for images
470  if (a == XA_PIXMAP)
471  formats.append(QLatin1String("image/ppm"));
472  }
473  return formats;
474 }
475 
476 //$$$
477 bool QX11Data::xdndMimeDataForAtom(Atom a, QMimeData *mimeData, QByteArray *data, Atom *atomFormat, int *dataFormat)
478 {
479  bool ret = false;
480  *atomFormat = a;
481  *dataFormat = 8;
482  QString atomName = xdndMimeAtomToString(a);
483  if (QInternalMimeData::hasFormatHelper(atomName, mimeData)) {
484  *data = QInternalMimeData::renderDataHelper(atomName, mimeData);
485  if (atomName == QLatin1String("application/x-color"))
486  *dataFormat = 16;
487  ret = true;
488  } else {
489  if ((a == ATOM(UTF8_STRING) || a == XA_STRING
490  || a == ATOM(TEXT) || a == ATOM(COMPOUND_TEXT))
491  && QInternalMimeData::hasFormatHelper(QLatin1String("text/plain"), mimeData)) {
492  if (a == ATOM(UTF8_STRING)){
493  *data = QInternalMimeData::renderDataHelper(QLatin1String("text/plain"), mimeData);
494  ret = true;
495  } else if (a == XA_STRING) {
497  QLatin1String("text/plain"), mimeData)).toLocal8Bit();
498  ret = true;
499  } else if (a == ATOM(TEXT) || a == ATOM(COMPOUND_TEXT)) {
500  // the ICCCM states that TEXT and COMPOUND_TEXT are in the
501  // encoding of choice, so we choose the encoding of the locale
503  QLatin1String("text/plain"), mimeData)).toLocal8Bit();
504  char *list[] = { strData.data(), NULL };
505 
506  XICCEncodingStyle style = (a == ATOM(COMPOUND_TEXT))
507  ? XCompoundTextStyle : XStdICCTextStyle;
508  XTextProperty textprop;
509  if (list[0] != NULL
510  && XmbTextListToTextProperty(X11->display, list, 1, style,
511  &textprop) == Success) {
512  *atomFormat = textprop.encoding;
513  *dataFormat = textprop.format;
514  *data = QByteArray((const char *) textprop.value, textprop.nitems * textprop.format / 8);
515  ret = true;
516 
517  DEBUG(" textprop type %lx\n"
518  " textprop name '%s'\n"
519  " format %d\n"
520  " %ld items\n"
521  " %d bytes\n",
522  textprop.encoding,
523  X11->xdndMimeAtomToString(textprop.encoding).toLatin1().data(),
524  textprop.format, textprop.nitems, data->size());
525 
526  XFree(textprop.value);
527  }
528  }
529  } else if (atomName == QLatin1String("text/x-moz-url") &&
530  QInternalMimeData::hasFormatHelper(QLatin1String("text/uri-list"), mimeData)) {
532  QLatin1String("text/uri-list"), mimeData).split('\n').first();
533  QString mozUri = QString::fromLatin1(uri, uri.size());
534  mozUri += QLatin1Char('\n');
535  *data = QByteArray(reinterpret_cast<const char *>(mozUri.utf16()), mozUri.length() * 2);
536  ret = true;
537  } else if ((a == XA_PIXMAP || a == XA_BITMAP) && mimeData->hasImage()) {
538  QPixmap pm = qvariant_cast<QPixmap>(mimeData->imageData());
539  if (a == XA_BITMAP && pm.depth() != 1) {
540  QImage img = pm.toImage();
542  pm = QPixmap::fromImage(img);
543  }
545  if (dm) {
546  Pixmap handle = pm.handle();
547  *data = QByteArray((const char *) &handle, sizeof(Pixmap));
550  (dm->xdndMimeTransferedPixmapIndex + 1) % 2;
551  ret = true;
552  }
553  } else {
554  DEBUG("QClipboard: xdndMimeDataForAtom(): converting to type '%s' is not supported", qPrintable(atomName));
555  }
556  }
557  return ret && data != 0;
558 }
559 
560 //$$$
562 {
563  QList<Atom> atoms;
564  atoms.append(xdndMimeStringToAtom(format));
565 
566  // special cases for strings
567  if (format == QLatin1String("text/plain")) {
568  atoms.append(ATOM(UTF8_STRING));
569  atoms.append(XA_STRING);
570  atoms.append(ATOM(TEXT));
571  atoms.append(ATOM(COMPOUND_TEXT));
572  }
573 
574  // special cases for uris
575  if (format == QLatin1String("text/uri-list")) {
576  atoms.append(xdndMimeStringToAtom(QLatin1String("text/x-moz-url")));
577  }
578 
579  //special cases for images
580  if (format == QLatin1String("image/ppm"))
581  atoms.append(XA_PIXMAP);
582  if (format == QLatin1String("image/pbm"))
583  atoms.append(XA_BITMAP);
584 
585  return atoms;
586 }
587 
588 //$$$
590 {
591  QString atomName = xdndMimeAtomToString(a);
592  if (atomName == format)
593  return data;
594 
595  if (!encoding.isEmpty()
596  && atomName == format + QLatin1String(";charset=") + QString::fromLatin1(encoding)) {
597 
598  if (requestedType == QVariant::String) {
600  if (codec)
601  return codec->toUnicode(data);
602  }
603 
604  return data;
605  }
606 
607  // special cases for string types
608  if (format == QLatin1String("text/plain")) {
609  if (a == ATOM(UTF8_STRING))
610  return QString::fromUtf8(data);
611  if (a == XA_STRING)
612  return QString::fromLatin1(data);
613  if (a == ATOM(TEXT) || a == ATOM(COMPOUND_TEXT))
614  // #### might be wrong for COMPUND_TEXT
615  return QString::fromLocal8Bit(data, data.size());
616  }
617 
618  // special case for uri types
619  if (format == QLatin1String("text/uri-list")) {
620  if (atomName == QLatin1String("text/x-moz-url")) {
621  // we expect this as utf16 <url><space><title>
622  // the first part is a url that should only contain ascci char
623  // so it should be safe to check that the second char is 0
624  // to verify that it is utf16
625  if (data.size() > 1 && data.at(1) == 0)
626  return QString::fromRawData((const QChar *)data.constData(),
627  data.size() / 2).split(QLatin1Char('\n')).first().toLatin1();
628  }
629  }
630 
631  // special cas for images
632  if (format == QLatin1String("image/ppm")) {
633  if (a == XA_PIXMAP && data.size() == sizeof(Pixmap)) {
634  Pixmap xpm = *((Pixmap*)data.data());
635  if (!xpm)
636  return QByteArray();
637  QPixmap qpm = QPixmap::fromX11Pixmap(xpm);
638  QImageWriter imageWriter;
639  imageWriter.setFormat("PPMRAW");
640  QImage imageToWrite = qpm.toImage();
641  QBuffer buf;
643  imageWriter.setDevice(&buf);
644  imageWriter.write(imageToWrite);
645  return buf.buffer();
646  }
647  }
648  return QVariant();
649 }
650 
651 //$$$ middle of xdndObtainData
653 {
654  encoding->clear();
655 
656  // find matches for string types
657  if (format == QLatin1String("text/plain")) {
658  if (atoms.contains(ATOM(UTF8_STRING)))
659  return ATOM(UTF8_STRING);
660  if (atoms.contains(ATOM(COMPOUND_TEXT)))
661  return ATOM(COMPOUND_TEXT);
662  if (atoms.contains(ATOM(TEXT)))
663  return ATOM(TEXT);
664  if (atoms.contains(XA_STRING))
665  return XA_STRING;
666  }
667 
668  // find matches for uri types
669  if (format == QLatin1String("text/uri-list")) {
670  Atom a = xdndMimeStringToAtom(format);
671  if (a && atoms.contains(a))
672  return a;
673  a = xdndMimeStringToAtom(QLatin1String("text/x-moz-url"));
674  if (a && atoms.contains(a))
675  return a;
676  }
677 
678  // find match for image
679  if (format == QLatin1String("image/ppm")) {
680  if (atoms.contains(XA_PIXMAP))
681  return XA_PIXMAP;
682  }
683 
684  // for string/text requests try to use a format with a well-defined charset
685  // first to avoid encoding problems
686  if (requestedType == QVariant::String
687  && format.startsWith(QLatin1String("text/"))
688  && !format.contains(QLatin1String("charset="))) {
689 
690  QString formatWithCharset = format;
691  formatWithCharset.append(QLatin1String(";charset=utf-8"));
692 
693  Atom a = xdndMimeStringToAtom(formatWithCharset);
694  if (a && atoms.contains(a)) {
695  *encoding = "utf-8";
696  return a;
697  }
698  }
699 
700  Atom a = xdndMimeStringToAtom(format);
701  if (a && atoms.contains(a))
702  return a;
703 
704  return 0;
705 }
706 
710 }
711 
712 
714 {
715  delete noDropCursor;
716  noDropCursor = 0;
717  delete copyCursor;
718  copyCursor = 0;
719  delete moveCursor;
720  moveCursor = 0;
721  delete linkCursor;
722  linkCursor = 0;
723  delete defaultPm;
724  defaultPm = 0;
725  delete xdnd_data.desktop_proxy;
726  xdnd_data.desktop_proxy = 0;
727  delete xdnd_data.deco;
728  xdnd_data.deco = 0;
729 }
730 
731 
732 static QWidget *find_child(QWidget *tlw, QPoint & p)
733 {
734  QWidget *widget = tlw;
735 
736  p = widget->mapFromGlobal(p);
737  bool done = false;
738  while (!done) {
739  done = true;
740  if (((QExtraWidget*)widget)->extraData() &&
741  ((QExtraWidget*)widget)->extraData()->xDndProxy != 0)
742  break; // stop searching for widgets under the mouse cursor if found widget is a proxy.
743  QObjectList children = widget->children();
744  if (!children.isEmpty()) {
745  for(int i = children.size(); i > 0;) {
746  --i;
747  QWidget *w = qobject_cast<QWidget *>(children.at(i));
748  if (!w)
749  continue;
751  continue;
752  if (w->isVisible() &&
753  w->geometry().contains(p) &&
754  !w->isWindow()) {
755  widget = w;
756  done = false;
757  p = widget->mapFromParent(p);
758  break;
759  }
760  }
761  }
762  }
763  return widget;
764 }
765 
766 
767 static bool checkEmbedded(QWidget* w, const XEvent* xe)
768 {
769  if (!w)
770  return false;
771 
772  if (current_embedding_widget != 0 && current_embedding_widget != w) {
773  qt_xdnd_current_target = ((QExtraWidget*)current_embedding_widget)->extraData()->xDndProxy;
778  current_embedding_widget = 0;
779  }
780 
781  QWExtra* extra = ((QExtraWidget*)w)->extraData();
782  if (extra && extra->xDndProxy != 0) {
783 
784  if (current_embedding_widget != w) {
785 
786  last_enter_event.xany.window = extra->xDndProxy;
787  XSendEvent(X11->display, extra->xDndProxy, False, NoEventMask, &last_enter_event);
788  current_embedding_widget = w;
789  }
790 
791  ((XEvent*)xe)->xany.window = extra->xDndProxy;
792  XSendEvent(X11->display, extra->xDndProxy, False, NoEventMask, (XEvent*)xe);
793  if (qt_xdnd_current_widget != w) {
794  qt_xdnd_current_widget = w;
795  }
796  return true;
797  }
798  current_embedding_widget = 0;
799  return false;
800 }
801 
802 void QX11Data::xdndHandleEnter(QWidget *, const XEvent * xe, bool /*passive*/)
803 {
804  motifdnd_active = false;
805 
806  last_enter_event.xclient = xe->xclient;
807 
808  const long *l = xe->xclient.data.l;
809  int version = (int)(((unsigned long)(l[1])) >> 24);
810 
811  if (version > xdnd_version)
812  return;
813 
814  qt_xdnd_dragsource_xid = l[0];
815 
816  int j = 0;
817  if (l[1] & 1) {
818  // get the types from XdndTypeList
819  Atom type = XNone;
820  int f;
821  unsigned long n, a;
822  unsigned char *retval = 0;
823  XGetWindowProperty(X11->display, qt_xdnd_dragsource_xid, ATOM(XdndTypelist), 0,
824  qt_xdnd_max_type, False, XA_ATOM, &type, &f,&n,&a,&retval);
825  if (retval) {
826  Atom *data = (Atom *)retval;
827  for (; j<qt_xdnd_max_type && j < (int)n; j++) {
828  qt_xdnd_types[j] = data[j];
829  }
830  XFree((uchar*)data);
831  }
832  } else {
833  // get the types from the message
834  int i;
835  for(i=2; i < 5; i++) {
836  qt_xdnd_types[j++] = l[i];
837  }
838  }
839  qt_xdnd_types[j] = 0;
840 }
841 
842 static void handle_xdnd_position(QWidget *w, const XEvent * xe, bool passive)
843 {
844  const unsigned long *l = (const unsigned long *)xe->xclient.data.l;
845 
846  QPoint p((l[2] & 0xffff0000) >> 16, l[2] & 0x0000ffff);
847  QWidget * c = find_child(w, p); // changes p to to c-local coordinates
848 
849  if (!passive && checkEmbedded(c, xe))
850  return;
851 
852  if (!c || (!c->acceptDrops() && (c->windowType() == Qt::Desktop)))
853  return;
854 
855  if (l[0] != qt_xdnd_dragsource_xid) {
856  DEBUG("xdnd drag position from unexpected source (%08lx not %08lx)", l[0], qt_xdnd_dragsource_xid);
857  return;
858  }
859 
860  // timestamp from the source
861  if (l[3] != 0) {
862  // Some X server/client combination swallow the first 32 bit and
863  // interpret a set bit 31 as negative sign.
864  qt_xdnd_target_current_time = X11->userTime =
865  ((sizeof(Time) == 8 && xe->xclient.data.l[3] < 0)
866  ? uint(l[3])
867  : l[3]);
868  }
869 
870  QDragManager *manager = QDragManager::self();
871  QMimeData *dropData = manager->object ? manager->dragPrivate()->data : manager->dropData;
872 
873  XClientMessageEvent response;
874  response.type = ClientMessage;
875  response.window = qt_xdnd_dragsource_xid;
876  response.format = 32;
877  response.message_type = ATOM(XdndStatus);
878  response.data.l[0] = w->effectiveWinId();
879  response.data.l[1] = 0; // flags
880  response.data.l[2] = 0; // x, y
881  response.data.l[3] = 0; // w, h
882  response.data.l[4] = 0; // action
883 
884  if (!passive) { // otherwise just reject
885  while (c && !c->acceptDrops() && !c->isWindow()) {
886  p = c->mapToParent(p);
887  c = c->parentWidget();
888  }
889  QWidget *target_widget = c && c->acceptDrops() ? c : 0;
890 
891  QRect answerRect(c->mapToGlobal(p), QSize(1,1));
892 
893  if (manager->object) {
895  } else {
896  possible_actions = Qt::DropActions(xdndaction_to_qtaction(l[4]));
897 // possible_actions |= Qt::CopyAction;
898  }
900 
901  Qt::DropAction accepted_action = Qt::IgnoreAction;
902 
903 
904  if (target_widget != qt_xdnd_current_widget) {
905  if (qt_xdnd_current_widget) {
906  QDragLeaveEvent e;
907  QApplication::sendEvent(qt_xdnd_current_widget, &e);
908  }
909  if (qt_xdnd_current_widget != target_widget) {
910  qt_xdnd_current_widget = target_widget;
911  }
912  if (target_widget) {
913  qt_xdnd_current_position = p;
914 
917  QApplication::sendEvent(target_widget, &de);
918  if (de.isAccepted() && de.dropAction() != Qt::IgnoreAction)
920  }
921  }
922 
923  DEBUG() << "qt_handle_xdnd_position action=" << X11->xdndAtomToString(l[4]);
924  if (!target_widget) {
925  answerRect = QRect(p, QSize(1, 1));
926  } else {
927  qt_xdnd_current_widget = c;
928  qt_xdnd_current_position = p;
929 
932  me.accept();
933  }
934  QApplication::sendEvent(c, &me);
935  if (me.isAccepted()) {
936  response.data.l[1] = 1; // yes
937  accepted_action = me.dropAction();
938  last_target_accepted_action = accepted_action;
939  } else {
940  response.data.l[0] = 0;
942  }
943  answerRect = me.answerRect().intersected(c->rect());
944  }
945  answerRect = QRect(c->mapToGlobal(answerRect.topLeft()), answerRect.size());
946 
947  if (answerRect.left() < 0)
948  answerRect.setLeft(0);
949  if (answerRect.right() > 4096)
950  answerRect.setRight(4096);
951  if (answerRect.top() < 0)
952  answerRect.setTop(0);
953  if (answerRect.bottom() > 4096)
954  answerRect.setBottom(4096);
955  if (answerRect.width() < 0)
956  answerRect.setWidth(0);
957  if (answerRect.height() < 0)
958  answerRect.setHeight(0);
959 
960  response.data.l[2] = (answerRect.x() << 16) + answerRect.y();
961  response.data.l[3] = (answerRect.width() << 16) + answerRect.height();
962  response.data.l[4] = qtaction_to_xdndaction(accepted_action);
963  }
964 
965  // reset
966  qt_xdnd_target_current_time = CurrentTime;
967 
969  if (source && (source->windowType() == Qt::Desktop) && !source->acceptDrops())
970  source = 0;
971 
972  DEBUG() << "sending XdndStatus";
973  if (source)
974  handle_xdnd_status(source, (const XEvent *)&response, passive);
975  else
976  XSendEvent(X11->display, qt_xdnd_dragsource_xid, False, NoEventMask, (XEvent*)&response);
977 }
978 
980 {
981  if (event->type != ClientMessage)
982  return false;
983  XClientMessageEvent *ev = &event->xclient;
984 
985  if (ev->message_type == ATOM(XdndPosition))
986  return true;
987 
988  return false;
989 }
990 
991 void QX11Data::xdndHandlePosition(QWidget * w, const XEvent * xe, bool passive)
992 {
993  DEBUG("xdndHandlePosition");
994  while (XCheckIfEvent(X11->display, (XEvent *)xe, xdnd_position_scanner, 0))
995  ;
996 
997  handle_xdnd_position(w, xe, passive);
998 }
999 
1000 
1001 static void handle_xdnd_status(QWidget *, const XEvent * xe, bool)
1002 {
1003  const unsigned long *l = (const unsigned long *)xe->xclient.data.l;
1004  // ignore late status messages
1005  if (l[0] && l[0] != qt_xdnd_current_proxy_target)
1006  return;
1007  Qt::DropAction newAction = (l[1] & 0x1) ? xdndaction_to_qtaction(l[4]) : Qt::IgnoreAction;
1008 
1009  if ((int)(l[1] & 2) == 0) {
1010  QPoint p((l[2] & 0xffff0000) >> 16, l[2] & 0x0000ffff);
1011  QSize s((l[3] & 0xffff0000) >> 16, l[3] & 0x0000ffff);
1012  qt_xdnd_source_sameanswer = QRect(p, s);
1013  } else {
1014  qt_xdnd_source_sameanswer = QRect();
1015  }
1016  QDragManager *manager = QDragManager::self();
1017  manager->willDrop = (l[1] & 0x1);
1018  if (global_accepted_action != newAction)
1019  manager->emitActionChanged(newAction);
1020  global_accepted_action = newAction;
1021  manager->updateCursor();
1022  waiting_for_status = false;
1023 }
1024 
1026 {
1027  if (event->type != ClientMessage)
1028  return false;
1029  XClientMessageEvent *ev = &event->xclient;
1030 
1031  if (ev->message_type == ATOM(XdndStatus))
1032  return true;
1033 
1034  return false;
1035 }
1036 
1037 void QX11Data::xdndHandleStatus(QWidget * w, const XEvent * xe, bool passive)
1038 {
1039  DEBUG("xdndHandleStatus");
1040  while (XCheckIfEvent(X11->display, (XEvent *)xe, xdnd_status_scanner, 0))
1041  ;
1042 
1043  handle_xdnd_status(w, xe, passive);
1044  DEBUG("xdndHandleStatus end");
1045 }
1046 
1047 void QX11Data::xdndHandleLeave(QWidget *w, const XEvent * xe, bool /*passive*/)
1048 {
1049  DEBUG("xdnd leave");
1050  if (!qt_xdnd_current_widget ||
1051  w->window() != qt_xdnd_current_widget->window()) {
1052  return; // sanity
1053  }
1054 
1055  if (checkEmbedded(current_embedding_widget, xe)) {
1056  current_embedding_widget = 0;
1057  qt_xdnd_current_widget = 0;
1058  return;
1059  }
1060 
1061  const unsigned long *l = (const unsigned long *)xe->xclient.data.l;
1062 
1063  QDragLeaveEvent e;
1064  QApplication::sendEvent(qt_xdnd_current_widget, &e);
1065 
1066  if (l[0] != qt_xdnd_dragsource_xid) {
1067  // This often happens - leave other-process window quickly
1068  DEBUG("xdnd drag leave from unexpected source (%08lx not %08lx", l[0], qt_xdnd_dragsource_xid);
1069  qt_xdnd_current_widget = 0;
1070  return;
1071  }
1072 
1074  qt_xdnd_types[0] = 0;
1075  qt_xdnd_current_widget = 0;
1076 }
1077 
1078 
1080 {
1082  return;
1083 
1084  QDragManager *manager = QDragManager::self();
1085 
1086  XClientMessageEvent leave;
1087  leave.type = ClientMessage;
1088  leave.window = qt_xdnd_current_target;
1089  leave.format = 32;
1090  leave.message_type = ATOM(XdndLeave);
1091  leave.data.l[0] = manager->dragPrivate()->source->effectiveWinId();
1092  leave.data.l[1] = 0; // flags
1093  leave.data.l[2] = 0; // x, y
1094  leave.data.l[3] = 0; // w, h
1095  leave.data.l[4] = 0; // just null
1096 
1098 
1099  if (w && (w->windowType() == Qt::Desktop) && !w->acceptDrops())
1100  w = 0;
1101 
1102  if (w)
1103  X11->xdndHandleLeave(w, (const XEvent *)&leave, false);
1104  else
1105  XSendEvent(X11->display, qt_xdnd_current_proxy_target, False,
1106  NoEventMask, (XEvent*)&leave);
1107 
1108  // reset the drag manager state
1109  manager->willDrop = false;
1113  manager->updateCursor();
1117  waiting_for_status = false;
1118 }
1119 
1120 void QX11Data::xdndHandleDrop(QWidget *, const XEvent * xe, bool passive)
1121 {
1122  DEBUG("xdndHandleDrop");
1123  if (!qt_xdnd_current_widget) {
1125  return; // sanity
1126  }
1127 
1128  if (!passive && checkEmbedded(qt_xdnd_current_widget, xe)){
1129  current_embedding_widget = 0;
1131  qt_xdnd_current_widget = 0;
1132  return;
1133  }
1134  const unsigned long *l = (const unsigned long *)xe->xclient.data.l;
1135 
1136  QDragManager *manager = QDragManager::self();
1137  DEBUG("xdnd drop");
1138 
1139  if (l[0] != qt_xdnd_dragsource_xid) {
1140  DEBUG("xdnd drop from unexpected source (%08lx not %08lx", l[0], qt_xdnd_dragsource_xid);
1141  return;
1142  }
1143 
1144  // update the "user time" from the timestamp in the event.
1145  if (l[2] != 0) {
1146  // Some X server/client combination swallow the first 32 bit and
1147  // interpret a set bit 31 as negative sign.
1148  qt_xdnd_target_current_time = X11->userTime =
1149  ((sizeof(Time) == 8 && xe->xclient.data.l[2] < 0)
1150  ? uint(l[2])
1151  : l[2]);
1152  }
1153 
1154  if (!passive) {
1155  // this could be a same-application drop, just proxied due to
1156  // some XEMBEDding, so try to find the real QMimeData used
1157  // based on the timestamp for this drop.
1158  QMimeData *dropData = 0;
1160  if (at != -1) {
1161  dropData = QDragManager::dragPrivate(X11->dndDropTransactions.at(at).object)->data;
1162  // Can't use the source QMimeData if we need the image conversion code from xdndObtainData
1163  if (dropData && dropData->hasImage())
1164  dropData = 0;
1165  }
1166  // if we can't find it, then use the data in the drag manager
1167  if (!dropData) {
1168  if (manager->object && !manager->dragPrivate()->data->hasImage())
1169  dropData = manager->dragPrivate()->data;
1170  else
1171  dropData = manager->dropData;
1172  }
1173 
1174  // Drop coming from another app? Update keyboard modifiers.
1175  if (!qt_xdnd_dragging) {
1177  }
1178 
1179  QDropEvent de(qt_xdnd_current_position, possible_actions, dropData,
1181  QApplication::sendEvent(qt_xdnd_current_widget, &de);
1182  if (!de.isAccepted()) {
1183  // Ignore a failed drag
1185  } else {
1187  }
1188  XClientMessageEvent finished;
1189  finished.type = ClientMessage;
1190  finished.window = qt_xdnd_dragsource_xid;
1191  finished.format = 32;
1192  finished.message_type = ATOM(XdndFinished);
1193  DNDDEBUG << "xdndHandleDrop"
1194  << "qt_xdnd_current_widget" << qt_xdnd_current_widget
1195  << (qt_xdnd_current_widget ? qt_xdnd_current_widget->effectiveWinId() : 0)
1196  << "t_xdnd_current_widget->window()"
1197  << (qt_xdnd_current_widget ? qt_xdnd_current_widget->window() : 0)
1198  << (qt_xdnd_current_widget ? qt_xdnd_current_widget->window()->internalWinId() : 0);
1199  finished.data.l[0] = qt_xdnd_current_widget?qt_xdnd_current_widget->window()->internalWinId():0;
1200  finished.data.l[1] = de.isAccepted() ? 1 : 0; // flags
1201  finished.data.l[2] = qtaction_to_xdndaction(global_accepted_action);
1202  XSendEvent(X11->display, qt_xdnd_dragsource_xid, False,
1203  NoEventMask, (XEvent*)&finished);
1204  } else {
1205  QDragLeaveEvent e;
1206  QApplication::sendEvent(qt_xdnd_current_widget, &e);
1207  }
1209  qt_xdnd_current_widget = 0;
1210  waiting_for_status = false;
1211 
1212  // reset
1213  qt_xdnd_target_current_time = CurrentTime;
1214 }
1215 
1216 
1217 void QX11Data::xdndHandleFinished(QWidget *, const XEvent * xe, bool passive)
1218 {
1219  DEBUG("xdndHandleFinished");
1220  const unsigned long *l = (const unsigned long *)xe->xclient.data.l;
1221 
1222  DNDDEBUG << "xdndHandleFinished, l[0]" << l[0]
1223  << "qt_xdnd_current_target" << qt_xdnd_current_target
1224  << "qt_xdnd_current_proxy_targe" << qt_xdnd_current_proxy_target;
1225 
1226  if (l[0]) {
1227  int at = findXdndDropTransactionByWindow(l[0]);
1228  if (at != -1) {
1230 
1231  QXdndDropTransaction t = X11->dndDropTransactions.takeAt(at);
1232  QDragManager *manager = QDragManager::self();
1233 
1234  Window target = qt_xdnd_current_target;
1235  Window proxy_target = qt_xdnd_current_proxy_target;
1236  QWidget *embedding_widget = current_embedding_widget;
1237  QDrag *currentObject = manager->object;
1238 
1241  current_embedding_widget = t.embedding_widget;
1242  manager->object = t.object;
1243 
1244  if (!passive)
1245  (void) checkEmbedded(qt_xdnd_current_widget, xe);
1246 
1247  current_embedding_widget = 0;
1250 
1251  if (t.object)
1252  t.object->deleteLater();
1253 
1254  qt_xdnd_current_target = target;
1255  qt_xdnd_current_proxy_target = proxy_target;
1256  current_embedding_widget = embedding_widget;
1257  manager->object = currentObject;
1258  }
1259  }
1260  waiting_for_status = false;
1261 }
1262 
1263 
1265 {
1266  if (e->timerId() == heartbeat && qt_xdnd_source_sameanswer.isNull()) {
1267  move(QCursor::pos());
1268  } else if (e->timerId() == transaction_expiry_timer) {
1269  for (int i = 0; i < X11->dndDropTransactions.count(); ++i) {
1270  const QXdndDropTransaction &t = X11->dndDropTransactions.at(i);
1271  if (t.targetWidget) {
1272  // dnd within the same process, don't delete these
1273  continue;
1274  }
1275  t.object->deleteLater();
1276  X11->dndDropTransactions.removeAt(i--);
1277  }
1278 
1281  }
1282 }
1283 
1285 {
1286  if (beingCancelled) {
1287  if (e->type() == QEvent::KeyRelease && ((QKeyEvent*)e)->key() == Qt::Key_Escape) {
1288  qApp->removeEventFilter(this);
1289  Q_ASSERT(object == 0);
1290  beingCancelled = false;
1291  eventLoop->exit();
1292  return true; // block the key release
1293  }
1294  return false;
1295  }
1296 
1297  Q_ASSERT(object != 0);
1298 
1299  if (!o->isWidgetType())
1300  return false;
1301 
1302  if (e->type() == QEvent::MouseMove) {
1303  QMouseEvent* me = (QMouseEvent *)e;
1304  move(me->globalPos());
1305  return true;
1306  } else if (e->type() == QEvent::MouseButtonRelease) {
1307  DEBUG("pre drop");
1308  qApp->removeEventFilter(this);
1309  if (willDrop)
1310  drop();
1311  else
1312  cancel();
1313  DEBUG("drop, resetting object");
1314  beingCancelled = false;
1315  eventLoop->exit();
1316  return true;
1317  }
1318 
1319  if (e->type() == QEvent::ShortcutOverride) {
1320  // prevent accelerators from firing while dragging
1321  e->accept();
1322  return true;
1323  }
1324 
1325  if (e->type() == QEvent::KeyPress || e->type() == QEvent::KeyRelease) {
1326  QKeyEvent *ke = ((QKeyEvent*)e);
1327  if (ke->key() == Qt::Key_Escape && e->type() == QEvent::KeyPress) {
1328  cancel();
1329  qApp->removeEventFilter(this);
1330  beingCancelled = false;
1331  eventLoop->exit();
1332  } else {
1333  qt_xdnd_source_sameanswer = QRect(); // force move
1334  move(QCursor::pos());
1335  }
1336  return true; // Eat all key events
1337  }
1338 
1339  // ### We bind modality to widgets, so we have to do this
1340  // ### "manually".
1341  // DnD is modal - eat all other interactive events
1342  switch (e->type()) {
1346  case QEvent::MouseMove:
1347  case QEvent::KeyPress:
1348  case QEvent::KeyRelease:
1349  case QEvent::Wheel:
1351 #ifdef QT3_SUPPORT
1352  case QEvent::Accel:
1353  case QEvent::AccelAvailable:
1354 #endif
1355  return true;
1356  default:
1357  return false;
1358  }
1359 }
1360 
1362 {
1363  if (!noDropCursor) {
1364 #ifndef QT_NO_CURSOR
1365  noDropCursor = new QCursor(Qt::ForbiddenCursor);
1366  moveCursor = new QCursor(Qt::DragMoveCursor);
1367  copyCursor = new QCursor(Qt::DragCopyCursor);
1368  linkCursor = new QCursor(Qt::DragLinkCursor);
1369 #endif
1370  }
1371 
1372  QCursor *c;
1373  if (willDrop) {
1375  c = copyCursor;
1376  } else if (global_accepted_action == Qt::LinkAction) {
1377  c = linkCursor;
1378  } else {
1379  c = moveCursor;
1380  }
1381  if (xdnd_data.deco) {
1382  xdnd_data.deco->show();
1383  xdnd_data.deco->raise();
1384  }
1385  } else {
1386  c = noDropCursor;
1387  //if (qt_xdnd_deco)
1388  // qt_xdnd_deco->hide();
1389  }
1390 #ifndef QT_NO_CURSOR
1391  if (c)
1392  qApp->changeOverrideCursor(*c);
1393 #endif
1394 }
1395 
1396 
1397 void QDragManager::cancel(bool deleteSource)
1398 {
1399  DEBUG("QDragManager::cancel");
1400  Q_ASSERT(heartbeat != -1);
1402  heartbeat = -1;
1403  beingCancelled = true;
1404  qt_xdnd_dragging = false;
1405 
1408 
1409 #ifndef QT_NO_CURSOR
1410  if (restoreCursor) {
1412  restoreCursor = false;
1413  }
1414 #endif
1415 
1416  if (deleteSource && object)
1417  object->deleteLater();
1418  object = 0;
1419  qDeleteInEventHandler(xdnd_data.deco);
1420  xdnd_data.deco = 0;
1421 
1423 }
1424 
1425 #ifndef QT_NO_SHAPE
1426 static
1427 bool windowInteractsWithPosition(const QPoint & pos, Window w, int shapeType)
1428 {
1429  int nrectanglesRet, dummyOrdering;
1430  XRectangle *rectangles = XShapeGetRectangles(QX11Info::display(), w, shapeType, &nrectanglesRet, &dummyOrdering);
1431  bool interacts = false;
1432  if (rectangles) {
1433  for (int i = 0; !interacts && i < nrectanglesRet; ++i)
1434  interacts = QRect(rectangles[i].x, rectangles[i].y, rectangles[i].width, rectangles[i].height).contains(pos);
1435  XFree(rectangles);
1436  }
1437  return interacts;
1438 }
1439 #endif
1440 
1441 static
1442 Window findRealWindow(const QPoint & pos, Window w, int md, bool ignoreNonXdndAwareWindows)
1443 {
1444  if (xdnd_data.deco && w == xdnd_data.deco->effectiveWinId())
1445  return 0;
1446 
1447  if (md) {
1448  X11->ignoreBadwindow();
1449  XWindowAttributes attr;
1450  XGetWindowAttributes(X11->display, w, &attr);
1451  if (X11->badwindow())
1452  return 0;
1453 
1454  if (attr.map_state == IsViewable
1455  && QRect(attr.x,attr.y,attr.width,attr.height).contains(pos)) {
1456  bool windowContainsMouse = !ignoreNonXdndAwareWindows;
1457  {
1458  Atom type = XNone;
1459  int f;
1460  unsigned long n, a;
1461  unsigned char *data;
1462 
1463  XGetWindowProperty(X11->display, w, ATOM(XdndAware), 0, 0, False,
1464  AnyPropertyType, &type, &f,&n,&a,&data);
1465  if (data) XFree(data);
1466  if (type) {
1467 #ifdef QT_NO_SHAPE
1468  return w;
1469 #else // !QT_NO_SHAPE
1470  const QPoint relPos = pos - QPoint(attr.x,attr.y);
1471  // When ShapeInput and ShapeBounding are not set they return a single rectangle with the geometry of the window, this is why we
1472  // need an && here so that in the case one is set and the other is not we still get the correct result.
1473 #if defined(ShapeInput) && defined(ShapeBounding)
1474  windowContainsMouse = windowInteractsWithPosition(relPos, w, ShapeInput) && windowInteractsWithPosition(relPos, w, ShapeBounding);
1475 #elif defined(ShapeBounding)
1476  windowContainsMouse = windowInteractsWithPosition(relPos, w, ShapeBounding);
1477 #else
1478  windowContainsMouse = true;
1479 #endif
1480  if (windowContainsMouse)
1481  return w;
1482 #endif // QT_NO_SHAPE
1483  }
1484  }
1485 
1486  Window r, p;
1487  Window* c;
1488  uint nc;
1489  if (XQueryTree(X11->display, w, &r, &p, &c, &nc)) {
1490  r=0;
1491  for (uint i=nc; !r && i--;) {
1492  r = findRealWindow(pos-QPoint(attr.x,attr.y),
1493  c[i], md-1, ignoreNonXdndAwareWindows);
1494  }
1495  XFree(c);
1496  if (r)
1497  return r;
1498 
1499  // We didn't find a client window! Just use the
1500  // innermost window.
1501  }
1502 
1503  // No children!
1504  if (!windowContainsMouse)
1505  return 0;
1506  else
1507  return w;
1508  }
1509  }
1510  return 0;
1511 }
1512 
1513 void QDragManager::move(const QPoint & globalPos)
1514 {
1515 #ifdef QT_NO_CURSOR
1516  Q_UNUSED(globalPos);
1517  return;
1518 #else
1519  DEBUG() << "QDragManager::move enter";
1520  if (!object) {
1521  // perhaps the target crashed?
1522  return;
1523  }
1524 
1525  int screen = QCursor::x11Screen();
1526  if ((qt_xdnd_current_screen == -1 && screen != X11->defaultScreen) || (screen != qt_xdnd_current_screen)) {
1527  // recreate the pixmap on the new screen...
1528  delete xdnd_data.deco;
1529  QWidget* parent = object->source()->window()->x11Info().screen() == screen
1530  ? object->source()->window() : QApplication::desktop()->screen(screen);
1531  xdnd_data.deco = new QShapedPixmapWidget(parent);
1532  if (!QWidget::mouseGrabber()) {
1533  updatePixmap();
1534  xdnd_data.deco->grabMouse();
1535  }
1536  }
1537  xdnd_data.deco->move(QCursor::pos() - xdnd_data.deco->pm_hot);
1538 
1539  if (qt_xdnd_source_sameanswer.contains(globalPos) && qt_xdnd_source_sameanswer.isValid())
1540  return;
1541 
1542  qt_xdnd_current_screen = screen;
1544  Window target = 0;
1545  int lx = 0, ly = 0;
1546  if (!XTranslateCoordinates(X11->display, rootwin, rootwin, globalPos.x(), globalPos.y(), &lx, &ly, &target))
1547  // some weird error...
1548  return;
1549 
1550  if (target == rootwin) {
1551  // Ok.
1552  } else if (target) {
1553  //me
1554  Window src = rootwin;
1555  while (target != 0) {
1556  DNDDEBUG << "checking target for XdndAware" << QWidget::find(target) << target;
1557  int lx2, ly2;
1558  Window t;
1559  // translate coordinates
1560  if (!XTranslateCoordinates(X11->display, src, target, lx, ly, &lx2, &ly2, &t)) {
1561  target = 0;
1562  break;
1563  }
1564  lx = lx2;
1565  ly = ly2;
1566  src = target;
1567 
1568  // check if it has XdndAware
1569  Atom type = 0;
1570  int f;
1571  unsigned long n, a;
1572  unsigned char *data = 0;
1573  XGetWindowProperty(X11->display, target, ATOM(XdndAware), 0, 0, False,
1574  AnyPropertyType, &type, &f,&n,&a,&data);
1575  if (data)
1576  XFree(data);
1577  if (type) {
1578  DNDDEBUG << "Found XdndAware on " << QWidget::find(target) << target;
1579  break;
1580  }
1581 
1582  // find child at the coordinates
1583  if (!XTranslateCoordinates(X11->display, src, src, lx, ly, &lx2, &ly2, &target)) {
1584  target = 0;
1585  break;
1586  }
1587  }
1588  if (xdnd_data.deco && (!target || target == xdnd_data.deco->effectiveWinId())) {
1589  DNDDEBUG << "need to find real window";
1590  target = findRealWindow(globalPos, rootwin, 6, true);
1591  if (target == 0)
1592  target = findRealWindow(globalPos, rootwin, 6, false);
1593  DNDDEBUG << "real window found" << QWidget::find(target) << target;
1594  }
1595  }
1596 
1597  QWidget* w;
1598  if (target) {
1599  w = QWidget::find((WId)target);
1600  if (w && (w->windowType() == Qt::Desktop) && !w->acceptDrops())
1601  w = 0;
1602  } else {
1603  w = 0;
1604  target = rootwin;
1605  }
1606 
1607  DNDDEBUG << "and the final target is " << QWidget::find(target) << target;
1608  DNDDEBUG << "the widget w is" << w;
1609 
1610  WId proxy_target = xdndProxy(target);
1611  if (!proxy_target)
1612  proxy_target = target;
1613  int target_version = 1;
1614 
1615  if (proxy_target) {
1616  Atom type = XNone;
1617  int r, f;
1618  unsigned long n, a;
1619  unsigned char *retval;
1620  X11->ignoreBadwindow();
1621  r = XGetWindowProperty(X11->display, proxy_target, ATOM(XdndAware), 0,
1622  1, False, AnyPropertyType, &type, &f,&n,&a,&retval);
1623  int *tv = (int *)retval;
1624  if (r != Success || X11->badwindow()) {
1625  target = 0;
1626  } else {
1627  target_version = qMin(xdnd_version,tv ? *tv : 1);
1628  if (tv)
1629  XFree(tv);
1630 // if (!(!X11->badwindow() && type))
1631 // target = 0;
1632  }
1633  }
1634 
1635  if (target != qt_xdnd_current_target) {
1638 
1639  qt_xdnd_current_target = target;
1640  qt_xdnd_current_proxy_target = proxy_target;
1641  if (target) {
1643  int flags = target_version << 24;
1644  QStringList fmts = QInternalMimeData::formatsHelper(dragPrivate()->data);
1645  for (int i = 0; i < fmts.size(); ++i) {
1646  QList<Atom> atoms = X11->xdndMimeAtomsForFormat(fmts.at(i));
1647  for (int j = 0; j < atoms.size(); ++j) {
1648  if (!types.contains(atoms.at(j)))
1649  types.append(atoms.at(j));
1650  }
1651  }
1652  if (types.size() > 3) {
1653  XChangeProperty(X11->display,
1654  dragPrivate()->source->effectiveWinId(), ATOM(XdndTypelist),
1655  XA_ATOM, 32, PropModeReplace,
1656  (unsigned char *)types.data(),
1657  types.size());
1658  flags |= 0x0001;
1659  }
1660  XClientMessageEvent enter;
1661  enter.type = ClientMessage;
1662  enter.window = target;
1663  enter.format = 32;
1664  enter.message_type = ATOM(XdndEnter);
1665  enter.data.l[0] = dragPrivate()->source->effectiveWinId();
1666  enter.data.l[1] = flags;
1667  enter.data.l[2] = types.size()>0 ? types.at(0) : 0;
1668  enter.data.l[3] = types.size()>1 ? types.at(1) : 0;
1669  enter.data.l[4] = types.size()>2 ? types.at(2) : 0;
1670  // provisionally set the rectangle to 5x5 pixels...
1671  qt_xdnd_source_sameanswer = QRect(globalPos.x() - 2,
1672  globalPos.y() -2 , 5, 5);
1673 
1674  DEBUG("sending Xdnd enter");
1675  if (w)
1676  X11->xdndHandleEnter(w, (const XEvent *)&enter, false);
1677  else if (target)
1678  XSendEvent(X11->display, proxy_target, False, NoEventMask, (XEvent*)&enter);
1679  waiting_for_status = false;
1680  }
1681  }
1682  if (waiting_for_status)
1683  return;
1684 
1685  if (target) {
1686  waiting_for_status = true;
1687 
1688  XClientMessageEvent move;
1689  move.type = ClientMessage;
1690  move.window = target;
1691  move.format = 32;
1692  move.message_type = ATOM(XdndPosition);
1693  move.window = target;
1694  move.data.l[0] = dragPrivate()->source->effectiveWinId();
1695  move.data.l[1] = 0; // flags
1696  move.data.l[2] = (globalPos.x() << 16) + globalPos.y();
1697  move.data.l[3] = X11->time;
1698  move.data.l[4] = qtaction_to_xdndaction(defaultAction(dragPrivate()->possible_actions, QApplication::keyboardModifiers()));
1699  DEBUG("sending Xdnd position");
1700 
1702 
1703  if (w)
1704  handle_xdnd_position(w, (const XEvent *)&move, false);
1705  else
1706  XSendEvent(X11->display, proxy_target, False, NoEventMask,
1707  (XEvent*)&move);
1708  } else {
1709  if (willDrop) {
1710  willDrop = false;
1711  updateCursor();
1712  }
1713  }
1714  DEBUG() << "QDragManager::move leave";
1715 #endif
1716 }
1717 
1718 
1719 void QDragManager::drop()
1720 {
1721  Q_ASSERT(heartbeat != -1);
1723  heartbeat = -1;
1724  qt_xdnd_dragging = false;
1725 
1727  return;
1728 
1729  qDeleteInEventHandler(xdnd_data.deco);
1730  xdnd_data.deco = 0;
1731 
1732  XClientMessageEvent drop;
1733  drop.type = ClientMessage;
1735  drop.format = 32;
1736  drop.message_type = ATOM(XdndDrop);
1737  drop.data.l[0] = dragPrivate()->source->effectiveWinId();
1738  drop.data.l[1] = 0; // flags
1739  drop.data.l[2] = X11->time;
1740 
1741  drop.data.l[3] = 0;
1742  drop.data.l[4] = 0;
1743 
1745 
1746  if (w && (w->windowType() == Qt::Desktop) && !w->acceptDrops())
1747  w = 0;
1748 
1749  QXdndDropTransaction t = {
1750  X11->time,
1753  w,
1755  object
1756  };
1757  X11->dndDropTransactions.append(t);
1759 
1760  if (w)
1761  X11->xdndHandleDrop(w, (const XEvent *)&drop, false);
1762  else
1763  XSendEvent(X11->display, qt_xdnd_current_proxy_target, False,
1764  NoEventMask, (XEvent*)&drop);
1765 
1769  current_embedding_widget = 0;
1770  object = 0;
1771 
1772 #ifndef QT_NO_CURSOR
1773  if (restoreCursor) {
1775  restoreCursor = false;
1776  }
1777 #endif
1778 }
1779 
1780 
1781 
1783 {
1784  if (qt_xdnd_current_target) {
1785  QDragManager *manager = QDragManager::self();
1786  if (manager->object) {
1789  manager->object->deleteLater();
1790  manager->object = 0;
1791  xdnd_data.deco->deleteLater(); //delay freeing to avoid crash QTBUG-19363
1792  xdnd_data.deco = 0;
1793  return true;
1794  }
1795  }
1796  if (qt_xdnd_dragsource_xid) {
1798  if (qt_xdnd_current_widget) {
1799  QApplication::postEvent(qt_xdnd_current_widget, new QDragLeaveEvent);
1800  qt_xdnd_current_widget = 0;
1801  }
1802  return true;
1803  }
1804  return false;
1805 }
1806 
1807 void QX11Data::xdndHandleSelectionRequest(const XSelectionRequestEvent * req)
1808 {
1809  if (!req)
1810  return;
1811  XEvent evt;
1812  evt.xselection.type = SelectionNotify;
1813  evt.xselection.display = req->display;
1814  evt.xselection.requestor = req->requestor;
1815  evt.xselection.selection = req->selection;
1816  evt.xselection.target = XNone;
1817  evt.xselection.property = XNone;
1818  evt.xselection.time = req->time;
1819 
1820  QDragManager *manager = QDragManager::self();
1821  QDrag *currentObject = manager->object;
1822 
1823  // which transaction do we use? (note: -2 means use current manager->object)
1824  int at = -1;
1825 
1826  // figure out which data the requestor is really interested in
1827  if (manager->object && req->time == qt_xdnd_source_current_time) {
1828  // requestor wants the current drag data
1829  at = -2;
1830  } else {
1831  // if someone has requested data in response to XdndDrop, find the corresponding transaction. the
1832  // spec says to call XConvertSelection() using the timestamp from the XdndDrop
1833  at = findXdndDropTransactionByTime(req->time);
1834  if (at == -1) {
1835  // no dice, perhaps the client was nice enough to use the same window id in XConvertSelection()
1836  // that we sent the XdndDrop event to.
1837  at = findXdndDropTransactionByWindow(req->requestor);
1838  }
1839  if (at == -1 && req->time == CurrentTime) {
1840  // previous Qt versions always requested the data on a child of the target window
1841  // using CurrentTime... but it could be asking for either drop data or the current drag's data
1842  Window target = findXdndAwareParent(req->requestor);
1843  if (target) {
1845  at = -2;
1846  else
1847  at = findXdndDropTransactionByWindow(target);
1848  }
1849  }
1850  }
1851  if (at >= 0) {
1853 
1854  // use the drag object from an XdndDrop tansaction
1855  manager->object = X11->dndDropTransactions.at(at).object;
1856  } else if (at != -2) {
1857  // no transaction found, we'll have to reject the request
1858  manager->object = 0;
1859  }
1860  if (manager->object) {
1861  Atom atomFormat = req->target;
1862  int dataFormat = 0;
1863  QByteArray data;
1864  if (X11->xdndMimeDataForAtom(req->target, manager->dragPrivate()->data,
1865  &data, &atomFormat, &dataFormat)) {
1866  int dataSize = data.size() / (dataFormat / 8);
1867  XChangeProperty (X11->display, req->requestor, req->property,
1868  atomFormat, dataFormat, PropModeReplace,
1869  (unsigned char *)data.data(), dataSize);
1870  evt.xselection.property = req->property;
1871  evt.xselection.target = atomFormat;
1872  }
1873  }
1874 
1875  // reset manager->object in case we modified it above
1876  manager->object = currentObject;
1877 
1878  // ### this can die if req->requestor crashes at the wrong
1879  // ### moment
1880  XSendEvent(X11->display, req->requestor, False, 0, &evt);
1881 }
1882 
1883 static QVariant xdndObtainData(const char *format, QVariant::Type requestedType)
1884 {
1885  QByteArray result;
1886 
1887  QWidget* w;
1888  QDragManager *manager = QDragManager::self();
1889  if (qt_xdnd_dragsource_xid && manager->object &&
1891  && (!(w->windowType() == Qt::Desktop) || w->acceptDrops()))
1892  {
1894  const QString mimeType = QString::fromLatin1(format);
1895  if (o->data->hasFormat(mimeType)) {
1896  result = o->data->data(mimeType);
1897  } else if (mimeType.startsWith(QLatin1String("image/")) && o->data->hasImage()) {
1898  // ### duplicated from QInternalMimeData::renderDataHelper
1899  QImage image = qvariant_cast<QImage>(o->data->imageData());
1900  QBuffer buf(&result);
1901  buf.open(QBuffer::WriteOnly);
1902  image.save(&buf, mimeType.mid(mimeType.indexOf(QLatin1Char('/')) + 1).toLatin1().toUpper());
1903  }
1904  return result;
1905  }
1906 
1907  QList<Atom> atoms;
1908  int i = 0;
1909  while ((qt_xdnd_types[i])) {
1910  atoms.append(qt_xdnd_types[i]);
1911  ++i;
1912  }
1913  QByteArray encoding;
1914  Atom a = X11->xdndMimeAtomForFormat(QLatin1String(format), requestedType, atoms, &encoding);
1915  if (!a)
1916  return result;
1917 
1918  if (XGetSelectionOwner(X11->display, ATOM(XdndSelection)) == XNone)
1919  return result; // should never happen?
1920 
1922  if (!qt_xdnd_current_widget || (qt_xdnd_current_widget->windowType() == Qt::Desktop))
1923  tw = new QWidget;
1924 
1925  XConvertSelection(X11->display, ATOM(XdndSelection), a, ATOM(XdndSelection), tw->effectiveWinId(),
1927  XFlush(X11->display);
1928 
1929  XEvent xevent;
1930  bool got=X11->clipboardWaitForEvent(tw->effectiveWinId(), SelectionNotify, &xevent, 5000);
1931  if (got) {
1932  Atom type;
1933 
1934  if (X11->clipboardReadProperty(tw->effectiveWinId(), ATOM(XdndSelection), true, &result, 0, &type, 0)) {
1935  if (type == ATOM(INCR)) {
1936  int nbytes = result.size() >= 4 ? *((int*)result.data()) : 0;
1937  result = X11->clipboardReadIncrementalProperty(tw->effectiveWinId(), ATOM(XdndSelection), nbytes, false);
1938  } else if (type != a && type != XNone) {
1939  DEBUG("Qt clipboard: unknown atom %ld", type);
1940  }
1941  }
1942  }
1943  if (!qt_xdnd_current_widget || (qt_xdnd_current_widget->windowType() == Qt::Desktop))
1944  delete tw;
1945 
1946  return X11->xdndMimeConvertToFormat(a, result, QLatin1String(format), requestedType, encoding);
1947 }
1948 
1949 
1950 /*
1951  Enable drag and drop for widget w by installing the proper
1952  properties on w's toplevel widget.
1953 */
1954 bool QX11Data::dndEnable(QWidget* w, bool on)
1955 {
1956  w = w->window();
1957 
1958  if (bool(((QExtraWidget*)w)->topData()->dnd) == on)
1959  return true; // been there, done that
1960  ((QExtraWidget*)w)->topData()->dnd = on ? 1 : 0;
1961 
1962  motifdndEnable(w, on);
1963  return xdndEnable(w, on);
1964 }
1965 
1967 {
1968  if (object == o || !o || !o->d_func()->source)
1969  return Qt::IgnoreAction;
1970 
1971  if (object) {
1972  cancel();
1973  qApp->removeEventFilter(this);
1974  beingCancelled = false;
1975  }
1976 
1977  if (object) {
1978  // the last drag and drop operation hasn't finished, so we are going to wait
1979  // for one second to see if it does... if the finish message comes after this,
1980  // then we could still have problems, but this is highly unlikely
1982 
1984  timer.start();
1985  do {
1986  XEvent event;
1987  // Pass the event through the event dispatcher filter so that applications
1988  // which install an event filter on the dispatcher get to handle it first.
1989  if (XCheckTypedEvent(X11->display, ClientMessage, &event) &&
1991  qApp->x11ProcessEvent(&event);
1992 
1993  // sleep 50 ms, so we don't use up CPU cycles all the time.
1994  struct timeval usleep_tv;
1995  usleep_tv.tv_sec = 0;
1996  usleep_tv.tv_usec = 50000;
1997  select(0, 0, 0, 0, &usleep_tv);
1998  } while (object && timer.hasExpired(1000));
1999  }
2000 
2001  object = o;
2002  object->d_func()->target = 0;
2003  xdnd_data.deco = new QShapedPixmapWidget(object->source()->window());
2004 
2005  willDrop = false;
2006 
2007  updatePixmap();
2008 
2009  qApp->installEventFilter(this);
2010  XSetSelectionOwner(X11->display, ATOM(XdndSelection), dragPrivate()->source->window()->internalWinId(), X11->time);
2012  qt_xdnd_source_sameanswer = QRect();
2013 #ifndef QT_NO_CURSOR
2014  // set the override cursor (must be done here, since it is updated
2015  // in the call to move() below)
2016  qApp->setOverrideCursor(Qt::ArrowCursor);
2017  restoreCursor = true;
2018 #endif
2019  move(QCursor::pos());
2020  heartbeat = startTimer(200);
2021 
2022  qt_xdnd_dragging = true;
2023 
2024  if (!QWidget::mouseGrabber())
2025  xdnd_data.deco->grabMouse();
2026 
2027  eventLoop = new QEventLoop;
2028  (void) eventLoop->exec();
2029  delete eventLoop;
2030  eventLoop = 0;
2031 
2032 #ifndef QT_NO_CURSOR
2033  if (restoreCursor) {
2034  qApp->restoreOverrideCursor();
2035  restoreCursor = false;
2036  }
2037 #endif
2038 
2039  // delete cursors as they may be different next drag.
2040  delete noDropCursor;
2041  noDropCursor = 0;
2042  delete copyCursor;
2043  copyCursor = 0;
2044  delete moveCursor;
2045  moveCursor = 0;
2046  delete linkCursor;
2047  linkCursor = 0;
2048 
2049  delete xdnd_data.deco;
2050  xdnd_data.deco = 0;
2051  if (heartbeat != -1)
2053  heartbeat = -1;
2055  qt_xdnd_dragging = false;
2056 
2057  return global_accepted_action;
2058  // object persists until we get an xdnd_finish message
2059 }
2060 
2062 {
2063  if (xdnd_data.deco) {
2064  QPixmap pm;
2066  if (object) {
2067  pm = dragPrivate()->pixmap;
2068  if (!pm.isNull())
2069  pm_hot = dragPrivate()->hotspot;
2070  }
2071  if (pm.isNull()) {
2072  if (!defaultPm)
2073  defaultPm = new QPixmap(default_pm);
2074  pm = *defaultPm;
2075  }
2076  xdnd_data.deco->pm_hot = pm_hot;
2077  xdnd_data.deco->setPixmap(pm);
2078  xdnd_data.deco->move(QCursor::pos()-pm_hot);
2079  xdnd_data.deco->show();
2080  }
2081 }
2082 
2083 QVariant QDropData::retrieveData_sys(const QString &mimetype, QVariant::Type requestedType) const
2084 {
2085  QByteArray mime = mimetype.toLatin1();
2086  QVariant data = X11->motifdnd_active
2087  ? X11->motifdndObtainData(mime)
2088  : xdndObtainData(mime, requestedType);
2089  return data;
2090 }
2091 
2092 bool QDropData::hasFormat_sys(const QString &format) const
2093 {
2094  return formats().contains(format);
2095 }
2096 
2098 {
2099  QStringList formats;
2100  if (X11->motifdnd_active) {
2101  int i = 0;
2102  QByteArray fmt;
2103  while (!(fmt = X11->motifdndFormat(i)).isEmpty()) {
2104  formats.append(QLatin1String(fmt));
2105  ++i;
2106  }
2107  } else {
2108  int i = 0;
2109  while ((qt_xdnd_types[i])) {
2110  QStringList formatsForAtom = X11->xdndMimeFormatsForAtom(qt_xdnd_types[i]);
2111  for (int j = 0; j < formatsForAtom.size(); ++j) {
2112  if (!formats.contains(formatsForAtom.at(j)))
2113  formats.append(formatsForAtom.at(j));
2114  }
2115  ++i;
2116  }
2117  }
2118  return formats;
2119 }
2120 
2122 
2123 #endif // QT_NO_DRAGANDDROP
The QVariant class acts like a union for the most common Qt data types.
Definition: qvariant.h:92
QPoint pos() const
int startTimer(int interval)
Starts a timer and returns a timer identifier, or returns zero if it could not start a timer...
Definition: qobject.cpp:1623
QBool contains(QChar c, Qt::CaseSensitivity cs=Qt::CaseSensitive) const
Definition: qstring.h:904
The QPainter class performs low-level painting on widgets and other paint devices.
Definition: qpainter.h:86
void updateCursor()
Definition: qdnd_mac.mm:268
QImage toImage() const
Converts the pixmap to a QImage.
Definition: qpixmap.cpp:542
QWidget * parentWidget() const
Returns the parent of this widget, or 0 if it does not have any parent widget.
Definition: qwidget.h:1035
Qt::DropActions possible_actions
Definition: qdnd_p.h:182
static QPixmap fromImage(const QImage &image, Qt::ImageConversionFlags flags=Qt::AutoColor)
Converts the given image to a pixmap using the specified flags to control the conversion.
Definition: qpixmap.cpp:2197
static int qtaction_to_xdndaction(Qt::DropAction a)
Definition: qdnd_x11.cpp:189
QPixmap xdndMimeTransferedPixmap[2]
Definition: qdnd_p.h:259
bool hasExpired(qint64 timeout) const
Returns true if this QElapsedTimer has already expired by timeout milliseconds (that is...
The QKeyEvent class describes a key event.
Definition: qevent.h:224
bool hasFormat_sys(const QString &mimeType) const
Definition: qdnd_mac.mm:214
unsigned long WId
Definition: qwindowdefs.h:119
void xdndHandlePosition(QWidget *, const XEvent *, bool)
Definition: qdnd_x11.cpp:991
bool isNull() const
Returns true if the rectangle is a null rectangle, otherwise returns false.
Definition: qrect.h:231
void grabMouse()
Grabs the mouse input.
static QString fromLocal8Bit(const char *, int size=-1)
Returns a QString initialized with the first size characters of the 8-bit string str.
Definition: qstring.cpp:4245
int type
Definition: qmetatype.cpp:239
QStringList formats_sys() const
Definition: qdnd_mac.mm:245
bool filterEvent(void *message)
Sends message through the event filter that was set by setEventFilter().
int y() const
The QCursor class provides a mouse cursor with an arbitrary shape.
Definition: qcursor.h:89
unsigned char c[8]
Definition: qnumeric_p.h:62
Q_DECL_CONSTEXPR const T & qMin(const T &a, const T &b)
Definition: qglobal.h:1215
static const int default_pm_hotx
Definition: qdnd_x11.cpp:260
QWidget * source() const
Returns the source of the drag object.
Definition: qdrag.cpp:209
#define QT_END_NAMESPACE
This macro expands to.
Definition: qglobal.h:90
The QDrag class provides support for MIME-based drag and drop data transfer.
Definition: qdrag.h:61
int width() const
Returns the width of the pixmap.
Definition: qpixmap.cpp:630
QWidget * desktop_proxy
Definition: qdnd_x11.cpp:318
QPointer< QWidget > widget
char * data()
Returns a pointer to the data stored in the byte array.
Definition: qbytearray.h:429
static Time qt_xdnd_target_current_time
Definition: qdnd_x11.cpp:233
static QPoint qt_xdnd_current_position
Definition: qdnd_x11.cpp:231
void qAddPostRoutine(QtCleanUpFunction p)
bool isWindow() const
Returns true if the widget is an independent window, otherwise returns false.
Definition: qwidget.h:945
WId effectiveWinId() const
Returns the effective window system identifier of the widget, i.
Definition: qwidget.cpp:2654
static void postEvent(QObject *receiver, QEvent *event)
Adds the event event, with the object receiver as the receiver of the event, to an event queue and re...
bool isVisible() const
Definition: qwidget.h:1005
static QAbstractEventDispatcher * instance(QThread *thread=0)
Returns a pointer to the event dispatcher object for the specified thread.
bool open(OpenMode openMode)
Reimplemented Function
Definition: qbuffer.cpp:338
QDrag * object
Definition: qdnd_p.h:238
static QWidget * find_child(QWidget *tlw, QPoint &p)
Definition: qdnd_x11.cpp:732
const int qt_xdnd_max_type
Definition: qdnd_x11.cpp:216
static Qt::DropAction xdndaction_to_qtaction(Atom atom)
Definition: qdnd_x11.cpp:178
#define at(className, varName)
QString xdndMimeAtomToString(Atom a)
Definition: qdnd_x11.cpp:433
The QByteArray class provides an array of bytes.
Definition: qbytearray.h:135
static Qt::HANDLE appRootWindow(int screen=-1)
Returns a handle for the applications root window on the given screen.
static Atom qt_xdnd_types[qt_xdnd_max_type+1]
Definition: qdnd_x11.cpp:217
static QStringList formatsHelper(const QMimeData *data)
Definition: qdnd.cpp:414
QString toUpper() const Q_REQUIRED_RESULT
Returns an uppercase copy of the string.
Definition: qstring.cpp:5483
The QWidget class is the base class of all user interface objects.
Definition: qwidget.h:150
void setDropAction(Qt::DropAction action)
Sets the action to be performed on the data by the target.
Definition: qevent.cpp:2746
Qt::DropAction dropAction() const
Returns the action to be performed on the data by the target.
Definition: qevent.h:494
int select(int, fd_set *, fd_set *, fd_set *, struct timeval *)
bool save(const QString &fileName, const char *format=0, int quality=-1) const
Saves the image to the file with the given fileName, using the given image file format and quality fa...
Definition: qimage.cpp:5346
const char * mime
void accept()
Calls QDropEvent::accept().
Definition: qevent.h:539
bool startsWith(const QString &s, Qt::CaseSensitivity cs=Qt::CaseSensitive) const
Returns true if the string starts with s; otherwise returns false.
Definition: qstring.cpp:3734
static bool xdndEnable(QWidget *w, bool on)
Definition: qdnd_x11.cpp:363
static QWidget * current_embedding_widget
Definition: qdnd_x11.cpp:249
QLatin1String(DBUS_INTERFACE_DBUS))) Q_GLOBAL_STATIC_WITH_ARGS(QString
Qt::HANDLE handle() const
Returns the pixmap&#39;s handle to the device context.
Definition: qpixmap.cpp:1299
long ASN1_INTEGER_get ASN1_INTEGER * a
QRect intersected(const QRect &other) const
Returns the intersection of this rectangle and the given rectangle.
Definition: qrect.h:481
static int findXdndDropTransactionByWindow(Window window)
Definition: qdnd_x11.cpp:94
static QCursor * copyCursor
Definition: qdnd_x11.cpp:255
QByteArray data(const QString &mimetype) const
Returns the data stored in the object in the format described by the MIME type specified by mimeType...
Definition: qmimedata.cpp:524
EventLoopTimerRef timer
void cancel(bool deleteSource=true)
Definition: qdnd_mac.mm:272
int depth() const
Returns the depth of the pixmap.
Definition: qpixmap.cpp:695
The QBuffer class provides a QIODevice interface for a QByteArray.
Definition: qbuffer.h:57
static QPixmap * defaultPm
Definition: qdnd_x11.cpp:258
static XEvent last_enter_event
Definition: qdnd_x11.cpp:250
The QString class provides a Unicode character string.
Definition: qstring.h:83
static Bool xdnd_status_scanner(Display *, XEvent *event, XPointer)
Definition: qdnd_x11.cpp:1025
T * qobject_cast(QObject *object)
Definition: qobject.h:375
The QDragMoveEvent class provides an event which is sent while a drag and drop action is in progress...
Definition: qevent.h:530
void emitActionChanged(Qt::DropAction newAction)
Definition: qdnd_p.h:253
#define Q_ASSERT(cond)
Definition: qglobal.h:1823
The QVector class is a template class that provides a dynamic array.
Definition: qdatastream.h:64
The QObject class is the base class of all Qt objects.
Definition: qobject.h:111
static Window qt_xdnd_current_proxy_target
Definition: qdnd_x11.cpp:226
#define X11
Definition: qt_x11_p.h:724
int height() const
The QElapsedTimer class provides a fast way to calculate elapsed times.
Definition: qelapsedtimer.h:53
Atom xdndStringToAtom(const char *)
Definition: qdnd_x11.cpp:425
QTLWExtra * topData()
Definition: qdnd_x11.cpp:332
The QChar class provides a 16-bit Unicode character.
Definition: qchar.h:72
QShapedPixmapWidget(QWidget *w)
Definition: qdnd_x11.cpp:282
static QString fromRawData(const QChar *, int size)
Constructs a QString that uses the first size Unicode characters in the array unicode.
Definition: qstring.cpp:7673
static QCursor * noDropCursor
Definition: qdnd_x11.cpp:253
static bool xdndHandleBadwindow()
Definition: qdnd_x11.cpp:1782
bool isEmpty() const
Returns true if the list contains no items; otherwise returns false.
Definition: qlist.h:152
Qt::DropAction drag(QDrag *)
Definition: qdnd_mac.mm:530
static QRect qt_xdnd_source_sameanswer
Definition: qdnd_x11.cpp:222
QStyle * style() const
Definition: qwidget.cpp:2742
static XdndData xdnd_data
Definition: qdnd_x11.cpp:321
static Window findRealWindow(const QPoint &pos, Window w, int md, bool ignoreNonXdndAwareWindows)
Definition: qdnd_x11.cpp:1442
union _XEvent XEvent
Definition: qwindowdefs.h:116
static QCursor * moveCursor
Definition: qdnd_x11.cpp:254
#define ATOM(x)
Definition: qt_x11_p.h:723
void update()
Updates the widget unless updates are disabled or the widget is hidden.
Definition: qwidget.cpp:10883
int key() const
Returns the code of the key that was pressed or released.
Definition: qevent.h:231
unsigned char uchar
Definition: qglobal.h:994
The QBitmap class provides monochrome (1-bit depth) pixmaps.
Definition: qbitmap.h:55
NSWindow * window
void append(const T &t)
Inserts value at the end of the list.
Definition: qlist.h:507
void clearMask()
Removes any mask set by setMask().
Definition: qwidget.cpp:13324
QWidget * embedding_widget
Definition: qt_x11_p.h:331
QWidget * targetWidget
Definition: qt_x11_p.h:330
#define QT_BEGIN_NAMESPACE
This macro expands to.
Definition: qglobal.h:89
Q_GUI_EXPORT EGLDisplay display()
Definition: qegl.cpp:589
bool isAccepted() const
Definition: qcoreevent.h:307
QBool contains(const T &t) const
Returns true if the list contains an occurrence of value; otherwise returns false.
Definition: qlist.h:880
static bool isEmpty(const char *str)
The QEventLoop class provides a means of entering and leaving an event loop.
Definition: qeventloop.h:55
void setPixmap(QPixmap pm)
Definition: qdnd_qws.cpp:102
friend class QPixmap
Definition: qwidget.h:748
static QWidget * mouseGrabber()
Returns the widget that is currently grabbing the mouse input.
bool testAttribute(Qt::WidgetAttribute) const
Returns true if attribute attribute is set on this widget; otherwise returns false.
Definition: qwidget.h:1041
void raise()
Raises this widget to the top of the parent widget&#39;s stack.
Definition: qwidget.cpp:11901
QByteArray & buffer()
Returns a reference to the QBuffer&#39;s internal buffer.
Definition: qbuffer.cpp:271
bool isEmpty() const
Returns true if the string has no characters; otherwise returns false.
Definition: qstring.h:704
The QImageWriter class provides a format independent interface for writing images to files or other d...
Definition: qimagewriter.h:59
QRect answerRect() const
Returns the rectangle in the widget where the drop will occur if accepted.
Definition: qevent.h:537
#define qApp
QWidget(QWidget *parent=0, Qt::WindowFlags f=0)
Constructs a widget which is a child of parent, with widget flags set to f.
Definition: qwidget.cpp:1189
int width() const
static QVariant xdndObtainData(const char *format, QVariant::Type requestedType)
Definition: qdnd_x11.cpp:1883
static Qt::DropAction last_target_accepted_action
Definition: qdnd_x11.cpp:242
void updatePixmap()
Definition: qdnd_mac.mm:696
const T & at(int i) const
Returns the item at index position i in the list.
Definition: qlist.h:468
The QStringList class provides a list of strings.
Definition: qstringlist.h:66
static QWidget * find(WId)
Returns a pointer to the widget with window identifer/handle id.
Definition: qwidget.cpp:2517
QWidgetData * data
Definition: qwidget.h:815
static QString fromUtf8(const char *, int size=-1)
Returns a QString initialized with the first size bytes of the UTF-8 string str.
Definition: qstring.cpp:4302
void append(const T &t)
Inserts value at the end of the vector.
Definition: qvector.h:573
static QCursor * linkCursor
Definition: qdnd_x11.cpp:256
static const int default_pm_hoty
Definition: qdnd_x11.cpp:261
int timerId() const
Returns the unique timer identifier, which is the same identifier as returned from QObject::startTime...
Definition: qcoreevent.h:346
The QImage class provides a hardware-independent image representation that allows direct access to th...
Definition: qimage.h:87
static const char * data(const QByteArray &arr)
unsigned int uint
Definition: qglobal.h:996
static bool hasFormatHelper(const QString &mimeType, const QMimeData *data)
Definition: qdnd.cpp:428
int indexOf(QChar c, int from=0, Qt::CaseSensitivity cs=Qt::CaseSensitive) const
Definition: qstring.cpp:2838
static void handle_xdnd_status(QWidget *w, const XEvent *xe, bool)
Definition: qdnd_x11.cpp:1001
The QLatin1String class provides a thin wrapper around an US-ASCII/Latin-1 encoded string literal...
Definition: qstring.h:654
static Window qt_xdnd_current_target
Definition: qdnd_x11.cpp:224
static QTextCodec * codec(MYSQL *mysql)
Definition: qsql_mysql.cpp:220
Type
This enum type defines the types of variable that a QVariant can contain.
Definition: qvariant.h:95
static bool sendEvent(QObject *receiver, QEvent *event)
Sends event event directly to receiver receiver, using the notify() function.
QBool contains(const QString &str, Qt::CaseSensitivity cs=Qt::CaseSensitive) const
Returns true if the list contains the string str; otherwise returns false.
Definition: qstringlist.h:172
static void split(QT_FT_Vector *b)
The QDragLeaveEvent class provides an event that is sent to a widget when a drag and drop action leav...
Definition: qevent.h:577
DropAction
Definition: qnamespace.h:1597
QByteArray toLatin1() const Q_REQUIRED_RESULT
Returns a Latin-1 representation of the string as a QByteArray.
Definition: qstring.cpp:3993
static bool checkEmbedded(QWidget *w, const XEvent *xe)
Definition: qdnd_x11.cpp:767
static WId xdndProxy(WId w)
Definition: qdnd_x11.cpp:335
static int transaction_expiry_timer
Definition: qdnd_x11.cpp:121
void show()
Shows the widget and its child widgets.
QWidget * source
Definition: qdnd_p.h:177
The QMimeData class provides a container for data that records information about its MIME type...
Definition: qmimedata.h:57
void paintEvent(QPaintEvent *)
This event handler can be reimplemented in a subclass to receive paint events passed in event...
Definition: qdnd_x11.cpp:307
static Atom qt_xdnd_dragsource_xid
Definition: qdnd_x11.cpp:213
QByteArray toLocal8Bit() const Q_REQUIRED_RESULT
Returns the local 8-bit representation of the string as a QByteArray.
Definition: qstring.cpp:4049
static Qt::DropAction global_accepted_action
Definition: qdnd_x11.cpp:245
void setMask(const QBitmap &)
Causes only the pixels of the widget for which bitmap has a corresponding 1 bit to be visible...
Definition: qwidget.cpp:13309
static QByteArray renderDataHelper(const QString &mimeType, const QMimeData *data)
Definition: qdnd.cpp:447
bool acceptDrops
whether drop events are enabled for this widget
Definition: qwidget.h:197
void xdndHandleLeave(QWidget *, const XEvent *, bool)
Definition: qdnd_x11.cpp:1047
QRegion mask() const
Returns the mask currently set on a widget.
Definition: qwidget.cpp:10058
void xdndHandleDrop(QWidget *, const XEvent *, bool)
Definition: qdnd_x11.cpp:1120
QWExtra * extraData()
Definition: qdnd_x11.cpp:331
#define Q_OBJECT
Definition: qobjectdefs.h:157
bool contains(const QPoint &p, bool proper=false) const
Returns true if the given point is inside or on the edge of the rectangle, otherwise returns false...
Definition: qrect.cpp:1101
static Qt::DropActions possible_actions
Definition: qdnd_x11.cpp:246
const T & at(int i) const
Returns the item at index position i in the vector.
Definition: qvector.h:350
bool willDrop
Definition: qdnd_p.h:244
QWidget * screen(int screen=-1)
bool qt_xdnd_dragging
Definition: qdnd_x11.cpp:237
The QMouseEvent class contains parameters that describe a mouse event.
Definition: qevent.h:85
static Bool xdnd_position_scanner(Display *, XEvent *event, XPointer)
Definition: qdnd_x11.cpp:979
static QDesktopWidget * desktop()
Returns the desktop widget (also called the root window).
QShapedPixmapWidget * deco
Definition: qdnd_x11.cpp:317
char * XPointer
Definition: qt_x11_p.h:180
void xdndHandleEnter(QWidget *, const XEvent *, bool)
Definition: qdnd_x11.cpp:802
static void xdndSetup()
Definition: qdnd_x11.cpp:707
static QDragManager * self()
Definition: qdnd.cpp:163
T & first()
Returns a reference to the first item in the list.
Definition: qlist.h:282
const char * constData() const
Returns a pointer to the data stored in the byte array.
Definition: qbytearray.h:433
Atom xdndMimeStringToAtom(const QString &mimeType)
Definition: qdnd_x11.cpp:445
QVariant imageData() const
Returns a QVariant storing a QImage if the object can return an image; otherwise returns a null varia...
Definition: qmimedata.cpp:442
bool hasImage() const
Returns true if the object can return an image; otherwise returns false.
Definition: qmimedata.cpp:471
QString toUnicode(const QByteArray &) const
Converts a from the encoding of this codec to Unicode, and returns the result in a QString...
QString mid(int position, int n=-1) const Q_REQUIRED_RESULT
Returns a string that contains n characters of this string, starting at the specified position index...
Definition: qstring.cpp:3706
virtual bool hasFormat(const QString &mimetype) const
Returns true if the object can return data for the MIME type specified by mimeType; otherwise returns...
Definition: qmimedata.cpp:563
QVariant retrieveData_sys(const QString &mimeType, QVariant::Type type) const
Definition: qdnd_mac.mm:229
static QPointer< QWidget > qt_xdnd_current_widget
Definition: qdnd_x11.cpp:230
QList< QByteArray > split(char sep) const
Splits the byte array into subarrays wherever sep occurs, and returns the list of those arrays...
void setDevice(QIODevice *device)
Sets QImageWriter&#39;s device to device.
struct _XDisplay Display
Definition: qwindowdefs.h:115
static void restartXdndDropExpiryTimer()
Definition: qdnd_x11.cpp:124
bool isWidgetType() const
Returns true if the object is a widget; otherwise returns false.
Definition: qobject.h:146
static Qt::KeyboardModifiers queryKeyboardModifiers()
Queries and returns the state of the modifier keys on the keyboard.
bool dndEnable(QWidget *w, bool on)
Definition: qdnd_x11.cpp:1954
static bool waiting_for_status
Definition: qdnd_x11.cpp:239
static Time qt_xdnd_source_current_time
Definition: qdnd_x11.cpp:227
QImage convertToFormat(Format f, Qt::ImageConversionFlags flags=Qt::AutoColor) const Q_REQUIRED_RESULT
Returns a copy of the image in the given format.
Definition: qimage.cpp:3966
QPoint mapFromParent(const QPoint &) const
Translates the parent widget coordinate pos to widget coordinates.
Definition: qwidget.cpp:4473
The QDropEvent class provides an event which is sent when a drag and drop action is completed...
Definition: qevent.h:476
static Qt::KeyboardModifiers keyboardModifiers()
Returns the current state of the modifier keys on the keyboard.
QByteArray xdndAtomToString(Atom a)
Definition: qdnd_x11.cpp:412
void setPixmap(const QPixmap &pm)
Definition: qdnd_x11.cpp:291
QString & append(QChar c)
Definition: qstring.cpp:1777
void qDeleteInEventHandler(QObject *o)
Definition: qobject.cpp:4348
#define DNDDEBUG
Definition: qdnd_x11.cpp:91
static void qt_xdnd_cleanup()
Definition: qdnd_x11.cpp:713
static Qt::KeyboardModifiers modifier_buttons
int x() const
void resize(int w, int h)
This corresponds to resize(QSize(w, h)).
Definition: qwidget.h:1014
QBitmap mask() const
Extracts a bitmap mask from the pixmap&#39;s alpha channel.
Definition: qpixmap.cpp:2077
The QTimerEvent class contains parameters that describe a timer event.
Definition: qcoreevent.h:341
static const struct @32 types[]
void setLeft(int pos)
Sets the left edge of the rectangle to the given x coordinate.
Definition: qrect.h:258
QRect rect
the internal geometry of the widget excluding any window frame
Definition: qwidget.h:168
Atom xdndMimeAtomForFormat(const QString &format, QVariant::Type requestedType, const QList< Atom > &atoms, QByteArray *requestedEncoding)
Definition: qdnd_x11.cpp:652
QMimeData * data
Definition: qdnd_p.h:179
static Window findXdndAwareParent(Window window)
Definition: qdnd_x11.cpp:133
static QString fromLatin1(const char *, int size=-1)
Returns a QString initialized with the first size characters of the Latin-1 string str...
Definition: qstring.cpp:4188
static int findXdndDropTransactionByTime(Time timestamp)
Definition: qdnd_x11.cpp:107
bool xdndMimeDataForAtom(Atom a, QMimeData *mimeData, QByteArray *data, Atom *atomFormat, int *dataFormat)
Definition: qdnd_x11.cpp:477
QDropData * dropData
Definition: qdnd_p.h:251
QObject * parent() const
Returns a pointer to the parent object.
Definition: qobject.h:273
The QDragEnterEvent class provides an event which is sent to a widget when a drag and drop action ent...
Definition: qevent.h:555
The QPoint class defines a point in the plane using integer precision.
Definition: qpoint.h:53
QPoint mapToParent(const QPoint &) const
Translates the widget coordinate pos to a coordinate in the parent widget.
Definition: qwidget.cpp:4459
int size() const
Returns the number of items in the list.
Definition: qlist.h:137
static void qt_xdnd_send_leave()
Definition: qdnd_x11.cpp:1079
if(void) toggleToolbarShown
The QRect class defines a rectangle in the plane using integer precision.
Definition: qrect.h:58
Definition: qnamespace.h:54
const int xdnd_version
Definition: qdnd_x11.cpp:176
QFactoryLoader * l
void xdndHandleStatus(QWidget *, const XEvent *, bool)
Definition: qdnd_x11.cpp:1037
static QTextCodec * codecForName(const QByteArray &name)
Searches all installed QTextCodec objects and returns the one which best matches name; the match is c...
const QObjectList & children() const
Returns a list of child objects.
Definition: qobject.h:197
T qvariant_cast(const QVariant &)
Definition: qvariant.h:571
WId internalWinId() const
Returns the window system identifier of the widget, or 0 if the widget is not created yet...
Definition: qwidget.h:244
int size() const
Returns the number of bytes in this byte array.
Definition: qbytearray.h:402
bool contains(const T &t) const
Returns true if the vector contains an occurrence of value; otherwise returns false.
Definition: qvector.h:731
int y() const
Returns the y coordinate of this point.
Definition: qpoint.h:131
void setAttribute(Qt::WidgetAttribute, bool on=true)
Sets the attribute attribute on this widget if on is true; otherwise clears the attribute.
Definition: qwidget.cpp:11087
QPoint mapFromGlobal(const QPoint &) const
Translates the global screen coordinate pos to widget coordinates.
QWidget * window() const
Returns the window for this widget, i.e.
Definition: qwidget.cpp:4492
The QPixmap class is an off-screen image representation that can be used as a paint device...
Definition: qpixmap.h:71
T * data() const
Definition: qpointer.h:79
void drawPixmap(const QRectF &targetRect, const QPixmap &pixmap, const QRectF &sourceRect)
Draws the rectangular portion source of the given pixmap into the given target in the paint device...
Definition: qpainter.cpp:5619
int height() const
Returns the height of the pixmap.
Definition: qpixmap.cpp:645
void setFormat(const QByteArray &format)
Sets the format QImageWriter will use when writing images, to format.
void xdndHandleFinished(QWidget *, const XEvent *, bool)
Definition: qdnd_x11.cpp:1217
static void initialize()
Definition: qcursor.cpp:417
void accept()
Sets the accept flag of the event object, the equivalent of calling setAccepted(true).
Definition: qcoreevent.h:309
bool isEmpty() const
Returns true if the byte array has size 0; otherwise returns false.
Definition: qbytearray.h:421
The QSize class defines the size of a two-dimensional object using integer point precision.
Definition: qsize.h:53
T * data()
Returns a pointer to the data stored in the vector.
Definition: qvector.h:152
Qt::WindowType windowType() const
Returns the window type of this widget.
Definition: qwidget.h:937
static Qt::MouseButtons mouseButtons()
Returns the current state of the buttons on the mouse.
#define Q_DECLARE_PRIVATE(Class)
Definition: qglobal.h:2467
int x() const
Returns the x coordinate of this point.
Definition: qpoint.h:128
void move(const QPoint &)
Definition: qdnd_mac.mm:283
bool event(QEvent *)
This is the main event handler; it handles event event.
Definition: qwidget.cpp:8636
static void restoreOverrideCursor()
Undoes the last setOverrideCursor().
bool isNull() const
Returns true if this is a null pixmap; otherwise returns false.
Definition: qpixmap.cpp:615
The QTextCodec class provides conversions between text encodings.
Definition: qtextcodec.h:62
bool isValid() const
Returns true if the rectangle is valid, otherwise returns false.
Definition: qrect.h:237
char at(int i) const
Returns the character at index position i in the byte array.
Definition: qbytearray.h:413
The QPaintEvent class contains event parameters for paint events.
Definition: qevent.h:298
QStringList xdndMimeFormatsForAtom(Atom a)
Definition: qdnd_x11.cpp:453
void drop()
Definition: qdnd_mac.mm:287
#define DEBUG
Definition: qdnd_x11.cpp:85
static int qt_xdnd_current_screen
Definition: qdnd_x11.cpp:235
bool write(const QImage &image)
Writes the image image to the assigned device or file name.
The QEvent class is the base class of all event classes.
Definition: qcoreevent.h:56
Type type() const
Returns the event type.
Definition: qcoreevent.h:303
#define qPrintable(string)
Definition: qglobal.h:1750
const QPoint & globalPos() const
Returns the global position of the mouse cursor at the time of the event.
Definition: qevent.h:96
bool eventFilter(QObject *, QEvent *)
Filters events if this object has been installed as an event filter for the watched object...
Definition: qdnd_mac.mm:263
QDragPrivate * dragPrivate() const
Definition: qdnd_p.h:231
#define Q_UNUSED(x)
Indicates to the compiler that the parameter with the specified name is not used in the body of a fun...
Definition: qglobal.h:1729
QRect geometry
the geometry of the widget relative to its parent and excluding the window frame
Definition: qwidget.h:158
int size() const
Returns the number of items in the vector.
Definition: qvector.h:137
QList< Atom > xdndMimeAtomsForFormat(const QString &format)
Definition: qdnd_x11.cpp:561
void start()
Starts this timer.
void deleteLater()
Schedules this object for deletion.
Definition: qobject.cpp:2145
QPoint mapToGlobal(const QPoint &) const
Translates the widget coordinate pos to global screen coordinates.
void xdndHandleSelectionRequest(const XSelectionRequestEvent *)
Definition: qdnd_x11.cpp:1807
The QLatin1Char class provides an 8-bit ASCII/Latin-1 character.
Definition: qchar.h:55
QVariant xdndMimeConvertToFormat(Atom a, const QByteArray &data, const QString &format, QVariant::Type requestedType, const QByteArray &encoding)
Definition: qdnd_x11.cpp:589
int xdndMimeTransferedPixmapIndex
Definition: qdnd_p.h:260
int exec(ProcessEventsFlags flags=AllEvents)
Enters the main event loop and waits until exit() is called.
Definition: qeventloop.cpp:181
static int heartbeat
Definition: qdnd_x11.cpp:220
void clear()
Clears the contents of the byte array and makes it empty.
static Display * display()
Returns the default display for the application.
static void flush()
Flushes the platform specific event queues.
void move(int x, int y)
This corresponds to move(QPoint(x, y)).
Definition: qwidget.h:1011
static QPoint pos()
Returns the position of the cursor (hot spot) in global screen coordinates.
Definition: qcursor_mac.mm:310
static void handle_xdnd_position(QWidget *, const XEvent *, bool)
Definition: qdnd_x11.cpp:842
static const char *const default_pm[]
Definition: qdnd_x11.cpp:262
The QList class is a template class that provides lists.
Definition: qdatastream.h:62
void timerEvent(QTimerEvent *)
This event handler can be reimplemented in a subclass to receive timer events for the object...
Definition: qdnd_mac.mm:259
QWidget * target() const
Returns the target of the drag and drop operation.
Definition: qdrag.cpp:219
static bool windowInteractsWithPosition(const QPoint &pos, Window w, int shapeType)
Definition: qdnd_x11.cpp:1427
void killTimer(int id)
Kills the timer with timer identifier, id.
Definition: qobject.cpp:1650
#define forever
This macro is provided for convenience for writing infinite loops.
Definition: qglobal.h:2452