Bentley Communities
Bentley Communities
  • Site
  • User
  • Site
  • Search
  • User
  • Welcome
  • Products
  • Support
  • About
  • More
  • Cancel
MicroStation
  • Product Communities
  • More
MicroStation
MicroStation Wiki Drag and Drop in MicroStation
    • Sign in

    • +MicroStation Wiki
    • +Administration Wiki
    • +Annotations Wiki
    • +Bentley View Wiki
    • +MicroStation PowerDraft
    • -Programming Wiki
      • A class to help create and modify text element
      • A Complete Example
      • A MicroStation VBA Example With Bentley ProjectWise
      • AddIn Development Using VB.NET
      • C# .NET Template with IPrimitiveCommandEvents Class
      • Capturing Graphics in Dynamic Views
      • Compiling MDL Applications
      • Database Manipulation
      • Debugging Native Code MDL Applications
      • Developing Code in VBA
      • Developing MicroStation Applications For DWG Files
      • Drag and Drop in MicroStation
      • Error: "Cannot save changes to VBA project 'Support' because it is read-only"
      • Getting And Setting Elements Using Graphic Groups In VBA [CS]
      • Getting Started with Visual Basic
      • How To Write A Recursive Routine In MicroStation VBA [CS]
      • Introducing Segment3D Methods In MicroStation V8 2004 Edition
      • Known issues in MDL and MicroStationAPI
      • Launching VBA Applications As Initapps Or Dgnapps [CS]
      • Learning MicroStation Addins Step by Step
      • MDL - Getting Started With XAttributes In MicroStation V8 XM Edition
      • MDL - Native Code Application Development
      • MDL Or MicroStation BASIC Choosing The Right Tool [TN]
      • MFC Dialog And Native Window Support
      • Microsoft Office VBA Patch Utility
      • MicroStation BASIC FAQ
      • MicroStation BASIC Limits [FAQ]
      • MicroStation Developer Documentation and Example Code
      • MicroStation Programming Advice
      • MicroStation SDK
      • MicroStation V8 Programming Tools Readme
      • MicroStation V8 VBA Programming Resources [CS]
      • MicroStation V8 XM Edition View Code Updates
      • MicroStation VBA Resources Revisited [CS]
      • Migrating Dimension Code To MicroStation V8
      • Migrating MDL Applications To Native Code
      • Mouse Wheel Events And The Visual Basic 6.0 IDE
      • Porting MDL Applications To MicroStation V8
      • Reading Elements From A Microsoft Access Database With VBA [CS]
      • Running MDL Applications
      • Scanning For MicroStation V8 Elements In VBA [CS]
      • Unleash A Workspace Wizard Automating Workspace Creation With MicroStation V8 And VBA [CS]
      • Using VBA To Detect The Current Or Last Used Command
      • Using VBA To Programmatically Export A VBA Project [CS]
      • Using VBA To Programmatically Import A VBA Projects Components And References [CS]
      • VBA -- Creating A Complex Application
      • VBA Interface Error: failed creating the comp manager - 0x80040583
      • VBA interface error: unable to get IDE
      • vba recording
      • Working With Levels In MicroStation VBA [CS]
      • Writing An MDL Application To Output Custom Placemarks To Google Earth
      • [V8i C++] PointCloud IPointCloudChannelDisplayHandler
    • +Visualization Wiki

     
     Questions about this article, topic, or product? Click here. 

    Drag and Drop in MicroStation

    As of MicroStation V8 2004 Edition, MicroStation dialog items can be Drag and Drop sources and targets. Data objects can be dragged within or among dialog items, or can be dragged to or from sources or targets outside MicroStation.

    Identifying a Dialog Item as a Drop Source or Target

    ListBoxes and Trees can be drop sources. To identify a dialog item as a drop source, add the EXTINTATTR_DROPSOURCE attribute to its dialog item resource definition (EXTINTATTR_DROPSOURCE and EXTINTATTR_DROPTARGET are defined in dlogbox.h):

    DItem_abcRsc abcID_yourItem =
    {
    . . .
    }
    extendedIntAttributes
    {
    {
    {EXTINTATTR_DROPSOURCE, 1}
    }
    };

    ListBoxes, Trees and Text items can be drop targets. To identify a ListBox or Tree as a drop target, add the EXTINTATTR_DROPTARGET attribute to its dialog item resource definition. All Text items are potentially drop targets without any changes to the resource definition. See more information about these items as drop targets in the "Drop Target Processing" section below.

    DItem_abcRsc abcID_yourItem =
    {
    . . .
    }
    extendedIntAttributes
    {
    {
    {EXTINTATTR_DROPTARGET, 1}
    }
    };

    A dialog item can be both a drop source and drop target.

    DItem_abcRsc abcID_yourItem =
    {
    . . .
    }
    extendedIntAttributes
    {
    {
    {EXTINTATTR_DROPSOURCE, 1},
    {EXTINTATTR_DROPTARGET, 1}
    }
    };

    The corresponding RawItemHdr variables to these extended attributes are

    riP->dropSource and
    riP->dropTarget.

    Clipboard Formats

    Drag and Drop applications use Windows clipboard formats to identify the type of data being dragged. The same clipboard format must be registered by both the drop source and drop target. Clipboard formats are registered using the mdlClipboard_registerClipboardFormat function.

    /* Same code is used by both the Drop Source and Drop Target */
    #define CLIPBOARD_FORMAT_MINE "My Clipboard Format Text"
    UShort cfFormat;
    cfFormat = mdlClipboard_registerClipboardFormat (CLIPBOARD_FORMAT_MINE);

    Drop Source Processing

    To implement drop source processing, the dialog item must have a hook. As the user starts a drag operation, the dialog item hook will receive a DITEM_MESSAGE_DROPSOURCE message with a dimP->u.dropSource.msgType of GUIDROPSOURCEMSG_BEGIN. The item hook is responsible for packaging the data to be dropped onto a drop target. This packaging is accomplished using the mdlDataObject_create function call.

    dimP->u.dropSource.pDataObject = mdlDataObject_create (cfFormat, pMyData, dataLen);

    The data object created will be available to the item hook in subsequent DITEM_MESSAGE_DROPSOURCE messages and is used in other mdlDataObject function calls, such as mdlDataObject_destroy.

    mdlDataObject_destroy (dimP->u.dropSource.pDataObject);

    Drop Source Message Types
    The DITEM_MESSAGE_DROPSOURCE message has several message subtypes (defined in dlogitem.h):

    • GUIDROPSOURCEMSG_BEGIN - received when the user starts a drag operation. See "BEGIN Responsibilities" below for more details.
    • GUIDROPSOURCEMSG_QUERY - received as the user drags the mouse
    • GUIDROPSOURCEMSG_PRECANCEL - received after the user cancels the drag operation but before the END message
    • GUIDROPSOURCEMSG_PREDROP - received after the user releases the mouse for the drop operation but before the DROP message
    • GUIDROPSOURCEMSG_DROP - received after the user releases the mouse for the drop operation. See "DROP Responsibilities" below for more details.
    • GUIDROPSOURCEMSG_END - received as a final message after the drag and drop operation has occurred. This message subtype is used to clean up the data object packaged during BEGIN processing. See "END Responsibilities" below for more details.

    Drop Source Message Structure
    DITEM_MESSAGE_DROPSOURCE and DialogItemMessage.u.dropSource are defined in dlogitem.h:

    struct
    {
    GUIDROPSOURCEMSG msgType;
    void *pDataObject;
    BoolInt bEscapePressed;
    UInt32 dwKeyState;
    UInt32 guiDropEffect;
    GUIDROPSTATUS guiDropStatus;
    } dropSource;
    BEGIN Responsibilities
    As mentioned previously, the item hook must package the data to be dropped. Additionally, the hook must establish the possible drop effects and set the drag and drop status to "OK": dimP->u.dropSource.pDataObject = mdlDataObject_create (cfFormat, pMyData, dataLen);
    dimP->u.dropSource.guiDropEffect =
    GUIDROPEFFECT_SCROLL|GUIDROPEFFECT_COPY|GUIDROPEFFECT_MOVE;
    dimP->u.dropSource.guiDropStatus = GUIDROPSTATUS_OK;

    DROP Responsibilities
    If the drop effect (guiDropEffect) includes GUIDROPEFFECT_MOVE and the drop target hasn't completely handled the move operation, the drop source item hook must remove or delete the data corresponding to the data object since it has been added to the drop target.

    END Responsibilities
    As the data object is created in the BEGIN processing, the data object must be destroyed in the END processing:

    mdlDataObject_destroy (dimP->u.dropSource.pDataObject);

    Drop Target Processing

    To implement drop target processing, the dialog item must have a hook. As the object is being dragged and released over the target item, the dialog item hook will receive a DITEM_MESSAGE_DROPTARGET message. The item hook should query the data object to determine if the item can accept the data object. The main mechanism for querying is to check the availability of a certain clipboard format in the data object using mdlDataObject_isFormatAvailable:

    bAvail = mdlDataObject_isFormatAvailable (dimP- >u.dropTarget.pDataObject, cfFormat);

    If the target item can accept the data object, a copy of the data is obtained using the mdlDataObject_getData function. This copy must be freed when no longer needed by calling the dlmSystem_mdlFree function.

    /* Get a copy of the data from the data object */
    pData = mdlDataObject_getData (dimP->u.dropTarget.pDataObject, cfFormat);
    . . .
    /* When no longer needed */
    dlmSystem_mdlFree (pData);

    If, for some reason, the target item does not want to accept the data object, the "Drop Effect" variable should be set to "None": Otherwise, the drag and drop subsystem will consider the item a valid drop target.

    dimP->u.dropTarget.guiDropEffect = GUIDROPEFFECT_NONE;

    Drop Target Message Types
    The DITEM_MESSAGE_DROPTARGET message has several message subtypes (defined in dlogitem.h):

    • GUIDROPTARGETMSG_ENTER - received as the user drags the mouse into the dialog item
    • GUIDROPTARGETMSG_OVER - received as the user drags the mouse over the dialog item
    • GUIDROPTARGETMSG_LEAVE - received as the user drags the mouse out of the dialog item
    • GUIDROPTARGETMSG_DROP - received as the user releases the mouse over the dialog item to effectively drop the data object

    Drop Source Message Structure
    DITEM_MESSAGE_DROPTARGET and DialogItemMessage.u.dropTarget are defined in dlogitem.h:

    struct
    {
    GUIDROPTARGETMSG msgType;
    void *pDataObject;
    UInt32 dwKeyState;
    Point2d localPt;
    UInt32 guiDropEffect;
    int iRow; /* For ListBoxes and Trees */
    int iCol;
    } dropTarget;

    DROP Responsibilities
    If the message type is DROP, the target can add the data object to itself in an appropriate manner for the application.

    /* If clipboard format is not available, disallow */
    if (!mdlDataObject_isFormatAvailable (dimP->u.dropTarget.pDataObject, cfFormat))
    dimP->u.dropTarget.guiDropEffect = GUIDROPEFFECT_NONE;

    /* If can't get the drop entry, disallow */
    else if (NULL == (pMyData =
    (MyData *) mdlDataObject_getData (dimP->u.dropTarget.pDataObject, cfFormat)))
    dimP->u.dropTarget.guiDropEffect = GUIDROPEFFECT_NONE;

    else
    {
    /* May further determine if this item can accept the data */
    /* If it cannot accept, set the guiDropEffect to GUIDROPEFFECT_NONE */
    . . .

    /* Use the copy of the data to add its contents to myself */
    if (GUIDROPTARGETMSG_DROP == dimP->u.dropTarget.msgType)
    {
    . . .
    }

    /* Free the copy from the Drag and Drop system */
    dlmSystem_mdlFree (pMyData);
    }

    ListBox Items as Drop Targets
    The default behavior is for the entire ListBox to be the drop target. In other words, if an object is dropped on a ListBox, the application usually inserts the object into a ListModel or StringList then sorts the list.

    If a drop between rows is desired, add the LISTATTRX_DROPBETWEENROWS extended attribute to the ListBox resource definition. When receiving the DITEM_MESSAGE_DROPTARGET, the DialogItemMessage.u.dropTarget.iRow member will contain the index of the row to insert before. If the drop target is below the last row in order to append, iRow will be -1. A visual representation will be shown where the row is to be inserted. This could be used by an application such as Customize where the insertion point for an object within a ListBox is important.

    Tree Items as Drop Targets
    The default behavior is for a particular tree node to be the drop target, and that tree node is temporarily highlighted. In other words, if an object is dropped on a Tree, the application usually "adds" the object to the tree node in a manner appropriate for the application. This could mean becoming part of the TreeModel's hierarchy or a member of a list owned by the tree node.

    If a drop onto the entire Tree is desired, add the TREEATTR_DROPWHOLEITEM extended attribute to the Tree resource definition. This could be used in an application such as Element Information where we want to analyze an element and update the entire dialog with that element's information.

    If a drop between rows is desired, add the TREEATTR_DROPBETWEENROWS attribute to the Tree resource definition. When receiving the DITEM_MESSAGE_DROPTARGET, the DialogItemMessage.u.dropTarget.iRow member will contain the index of the row to insert before. If the drop target is below the last row in order to append, iRow will be -1. A visual representation will be shown where the row is to be inserted. This could be used by an application where the ordering of Tree nodes/rows is important.

    Text Items as Drop Targets
    All Text items are potentially drop targets without any changes to their resource definitions if CF_TEXT, CF_UNICODETEXT or CF_HDROP clipboard formats are available in the data object. See mdlDataObject_getDragFileCount and mdlDataObject_getDragFile below in "mdlDataObject Functions" for more information on the HDROP format. To disallow a drop onto a Text item, include the following code in the Text item's hook:

    case DITEM_MESSAGE_DROPTARGET:
    /* Disallow a drop onto this Text item */
    dimP->msgUnderstood = TRUE;
    dimP->u.dropTarget.guiDropEffect = GUIDROPEFFECT_NONE;
    break;

    mdlDataObject Functions

    The Dialog Item Drag and Drop subsystem in MicroStation utilizes the Windows DoDragDrop function and the IDataObject, IDropSource and IDropTarget COM interfaces. The data object packaged by the drop source must implement the IDataObject interface. The data object created by the mdlDataObject_create function creates such an object. Other mdlDataObject functions are also provided which are simply front-ends to the IDataObject interface. If your application is written in C++, you may very well want to create your own class derived from IDataObject instead of using the mdlDataObject functions. This is quite acceptable. The following is a brief overview of the mdlDataObject functions, which are prototyped in msdragdrop.fdf.

    The GuiDataObject type is simply void.

    • mdlDataObject_create - Creates a GuiDataObject to be used in further Drag and Drop functions. A pointer to application data is passed in and associated with the GuiDataObject. The application retains ownership of the application data and is responsible for freeing the data after the drag and drop operation ends (see GUIDROPSOURCEMSG_END). A pointer to this data is retrieved using mdlDataObject_getApplicationData.
    • mdlDataObject_destroy - Destroys a GuiDataObject
    • mdlDataObject_getApplicationData - Retrieves a pointer to the application data provided to mdlDataObject_create or mdlDataObject_addFormat
    • mdlDataObject_addFormat - Adds a clipboard format and associated data to the GuiDataObject.
    • mdlDataObject_isFormatAvailable - Determines whether a particular clipboard format is associated with the GuiDataObject.
    • mdlDataObject_getData - Retrieves a copy of the data from the GuiDataObject. The caller is responsible for freeing the data returned by calling dlmSystem_mdlFree.
    • mdlDataObject_getDataHere - Retrieves the data from the GuiDataObject and copies it into the caller-supplied buffer.
    • mdlDataObject_getIDataObject - Retrieves the Windows IDataObject interface pointer.
    • mdlDataObject_getDragFileCount - Retrieves the number of files listed in a CF_HDROP data object.
    • mdlDataObject_getDragFile - Retrieves the file name at a certain index within a CF_HDROP data object.

    mdlWindow_dragDrop Functions

    The mdlWindow_dragDrop functions are primarily used internally by the Dialog Manager. However, in some rare cases, applications may need to call the following functions, which are prototyped in msdragdrop.fdf.

    • mdlWindow_dragDropRegister - Registers a window as a possible drop target
    • mdlWindow_dragDropRevoke - Unregisters/revokes a window as a possible drop target
    • mdlWindow_dragDropHasTarget - Sets/clears a window's "has a drop target" flag
    • mdlWindow_dragDropDo - Starts a Drag & Drop operation
    • Share
    • History
    • More
    • Cancel
    • Dan Koval Created by Bentley Colleague Dan Koval
    • When: Thu, Sep 5 2013 4:19 PM
    • Revisions: 1
    • Comments: 0
    Recommended
    Related
    Communities
    • Home
    • Getting Started
    • Community Central
    • Products
    • Support
    • Secure File Upload
    • Feedback
    Support and Services
    • Home
    • Product Support
    • Downloads
    • Subscription Services Portal
    Training and Learning
    • Home
    • About Bentley Institute
    • My Learning History
    • Reference Books
    Social Media
    •    LinkedIn
    •    Facebook
    •    Twitter
    •    YouTube
    •    RSS Feed
    •    Email

    © 2021 Bentley Systems, Incorporated  |  Contact Us  |  Privacy |  Terms of Use  |  Cookies