Skip to content

Instantly share code, notes, and snippets.

@phoe
Created February 25, 2018 15:22
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save phoe/da83c24a5b5a7f4baffed816fe2ad837 to your computer and use it in GitHub Desktop.
Save phoe/da83c24a5b5a7f4baffed816fe2ad837 to your computer and use it in GitHub Desktop.
Qtools UI drag and drop

Qtools UI - Drag and Drop

This module contains classes implementing drag and drop functionality inside Qtools UI.

Concept

Drag and drop functionality in Qt revolves around MIME types. A single drag can contain data in multiple formats, each of them described by a single MIME type in form of a string.

For simplicity, the mechanism used in this implementation uses only a single MIME type, which, by default, is "application/qtools-mime-data-with-object", being the value of *MIME-DATA-WITH-OBJECT-TYPE*.

You can provide your own separate MIME type by providing a :MIME-TYPE keyword argument to the constructors of DRAGGABLE and DROP-TARGET or client classes that subclass them. This can be used to create several drag and drop mechanisms that should not interact with each other, for example, when your application makes it possible to drag around multiple mutually incompatible types of data.

Class MIME-DATA-WITH-OBJECT

This class is a direct subclass of QMimeData with two modifications.

  • One of them is a slot called OBJECT that can be used to transmit arbitrary Lisp data via drag and drop.
  • The other is the :MIME-TYPE constructor keyword. This keyword can be used to provide the MIME type of the dragged data.

Class MIME-DATA-WITH-OBJECT is not meant to be instantiated directly by the user as it is a part of this drag and drop framework. Instead, the user should subclass class DRAGGABLE

Class DRAGGABLE

This class should be subclassed by all widgets that are meant to be draggable. Mouse-clicking an instance of this class will initiate drag behaviour.

Each DRAGGABLE has a MIME-TYPE slot, describing the MIME type of the content that is being dragged around. Its value must be a string and defaults to the value of *MIME-DATA-WITH-OBJECT-TYPE*.

This class overrides MOUSE-PRESS-EVENT.

Class DROP-TARGET

This class should be subclassed by all widgets that are meant to accept drops. Dropping a drag over this widget will initiate drop behaviour.

Each DROP-TARGET has a MIME-TYPE slot, describing the MIME type of the content that is acceptable for dropping. Its value must be a string and defaults to the value of *MIME-DATA-WITH-OBJECT-TYPE*.

This class overrides DRAG-ENTER-EVENT and DROP-EVENT.

Generic Function DROP-ACCEPTABLE-P

Syntax: (drop-acceptable-p item target)

Returns a boolean stating whether it is possible to drop ITEM onto TARGET.

To make it possible to drop item of class A onto an object of class B, define a method (defmethod drop-acceptable-p ((item A) (target B)) T). Keep in mind that the MIME types of the DRAGGABLE and DROP-TARGET in question must match, even if such a method is defined on both classes. (This is why we use a single MIME type for everything - to move the drag-and-drop dispatch to the Common Lisp GF mechanism.)

This generic function has a default method that returns NIL.

A method is provided for MIME-DATA-WITH-OBJECT that returns T.

Generic Function DROP

Syntax: (drop item target)

This generic function implements the consequences of dropping ITEM onto TARGET.

No default methods are provided for this method.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment