Dynamically control whether a control can be dropped

2 posts, 0 answers
  1. Carol Kilner
    Carol Kilner avatar
    1 posts
    Member since:
    May 2009

    Posted 07 Dec 2010 Link to this post

    I have some user controls that can drag/drop between a number of canvases. Some of the user controls also contain a number canvases that allows drag/drop action within the user control. I like the child elements that belongs to the canvases inside the user control to be able to drag/drop between canvases inside the user control, but not to the canvas that holds the user control (user control's parent canvas).

    I tried to assign names to the Tag properties to identify the nest level of droppable canvases and attempt to allow/restrict the drop in the OnDropQuery event handler by something like:

    private void OnDropQuery(object sender, DragDropQueryEventArgs e)
        var destination = e.Options.Destination;
        if (e.Options.Status == DragStatus.DropDestinationQuery)
            Canvas sourceCanvas = e.Options.Source.Parent as Canvas;
            if (sourceCanvas != null && destination.Tag == sourceCanvas.Tag)
                e.QueryResult = true;
                e.QueryResult = false;
            e.Handled = true;

    The issue is e.Options.Source.Parent has become a ContentControl instead of the source canvas that holds the dragging item.

    In my OnDragInfo handler, I have no problem getting the container canvas by the following:

    private void OnDragInfo(object sender, DragDropEventArgs e)
        FrameworkElement me = e.Options.Source as FrameworkElement;
        Canvas container = me.Parent as Canvas;
        if (container != null)
            if (e.Options.Status == DragStatus.DragComplete)
                // Only allow drag-drop within the same container

    I found out e.Options.Source.Parent sometimes change to ContentControl depending on e.Options.Status. For example, in OnDragQuery, I can use e.Options.Source.Parent to get the container canvas if e.Options.Status is DragQuery, but it becomes ContentControl if status is DropSourceQuery.

    What is the proper way to get the source container of the dragging item? Is there a better way to implement my nested drag/drop situation without using the Tag trick?
  2. Tsvyatko
    Tsvyatko avatar
    863 posts

    Posted 09 Dec 2010 Link to this post

    Hi Carol Kilner,

    You can take advantage of the fact that dropQuery has bubble execution strategy and bubbles through the visual tree and hold additional information in the  payload.

    Thus you can implement logic similar to the following:

    1. Create simple class e.g. DragPayload containing two properties the object being dragged and the parent (or information to identify it) being dragged from and use it in e.options.payload.

     - attach both to child and parent DropQuery
     - do not handle the event in the child canvas
     - check the conditions in the child canvas and set e.QueryResult if drop is possible
     - check the conditions in the parent canvas and set e.QueryResult if drop is possible Only if the e.Options.QueryResult is null (the child DropQuery is not raised).

    Let me know if this works in your case.

    Best wishes,
    the Telerik team
    Browse the videos here>> to help you get started with RadControls for Silverlight
Back to Top