Multiple DataTemplates
If we use the same DataTemplate for each of the sources, in our case ListBoxes, then dropping the item would have no issues in
displaying the dropped data in a ListBox. But assume a scenario where we need to have different DataTemplates for each ListBox with
a different Context, which also means a different Entity. The target ListBox would be unable to display the data, though the
content would be added. So to achieve the goal we need to have a Panel where UIElements are displayed regardless of any
DataTamplate.
Requirements to build the application
We need to have the followings to proceed:
- Visual Studio 2010
- Silverlight 4
- Silverlight 4 Toolkit
Create Silverlight Application
Fire up Visual Studio 2010, create a Silverlight Application and select the version as .Net Framework 4, then give the solution
a name such as DragDropMultipleItems.
As we have discussed about multiple DataContexts, let's create 3 entities such as
"StoryboardImage", "StoryboardMedia" and "StoryboardTransition". We will have few properties to demonstrate the concept.
Here
is the class definition of each entity.
Design the Application
We will have 3 ListBoxes for displaying data which can be dragged as source. A StackPanel will behave as the target control to
receive and keep the dropped objects.
Here is the basic design.

Adding DragDrop Controls to the Application
Silverlight 4 Toolkit provides DragDropTarget controls such as:
- ListBoxDragDropTarget
- PanelDragDropTarget
- TreeViewDragDropTarget
In our case we will use the first two, ListBoxDragDropTarget and PanelDragDropTarget. Adding the controls is very simple,
just add the source or target inside it. After adding the controls the Control stack would look like the following.

By default
when you add the above DragDropTargets the HorizontalContentAlignment property is set to Center, so the
content is not displayed properly. To fix that we have to set the HorizontalContentAlignment property to
Stretch for each one.
Adding the DataTemplate of each ListBox as UserControl
As we have discussed about different DataContexts for each ListBox, let's elaborate on this. We will have the DataTemplate of
the ListBoxes to different UserControls. We have 3 ListBoxes of type Image, Media, and Transition. So let's add 3
UserControls.

As you can see in the above figure, three UserControls are added to the Application. Now we will design it as
follows:



Setting the data for each UserControl can be done with Bindings as well as in C# code behind. For simplicity let's set the
properties in code behind. To do that we need to have an overloaded constructor where we will pass the information and set the
control's properties. The following example demonstrates it for a single UserControl; you can refer to the sample application for
the whole code.
Now that we have all set, let's load some sample data in the application. We have an Assets folder where we have
images for Image and Videos. To reference the Uri you need to set the BuildAction property of each image to
Content. If the property is set as Resource then we would need to set the Uri differently.
The
following code shows loading sample data for Images; you can refer to the sample application for the complete code.
We have not defined the AllowDrop property of the target PanelDragDropTarget yet. So let's set it to
true for achieving the DragDrop functionality.
We are ready to run the application for testing drag and drop.

While dragging the object the dragged content
is displayed and if there is a Drop Target then the icon changes to an Arrow or to Not Allowed. As follows:


As you can
see in the above figure, we have successfully loaded the ListBoxes and dragging and dropping of items from different ListBoxes to
Panel is displayed properly.
We have talked about the rule in the first section of this article. Let's see what is that
rule. Assume that this is a video playing application, where we need to have Videos, Images and Transitions. After adding the items
to the Storyboard (the dropped traget), it should start playing. The rule is that each Image or Video should be prefixed with a
Transition effect. And the first element of the Storyboard can only be Image or Video. So that whenever a Video or Image finishes
playing the transition to bring up the next item would have a effect.
I had tried few logics, but turned out to be complex
and not working. Finally I came up with a simple logic which fulfills the required rule.
As the rule says, we should have
Image or Video in 0th or even positions and the Transition to be in Odd positions always. So let's add the Tag
property to each UserControl and set it to 0 or 1. So that when we drop the element to the panel it
would compare the last element in the StackPanel (target drop Panel) with the Tag property.
For the comparison
we need to have the modulo operation so that it would always give you the remainder of the calculation. To understand it see the
code below.
When to check the rule
I have tried with few events such as the Drop event of PanelDragDropTarget and the MouseLeftButtonUp
event for the StackPanel. Using the mentioned events you will definitely get the dragged data or the Child count of the StackPanel
but it would fail for the first item or to get the last item.
That's why I came up with this LayoutUpdated
event for the StackPanel, which fires before the above two events and updates the Child count of the Stack Panel.
Now that we
have implemented the rule, let's test the application one more time.

As you see in the above figure the rule is applied to
the Drag Drop functionality. Try the sample application to verify it.
Conclusion
We have successfully achieved a drag operation from multiple ListBoxes with different data templates and data contexst, and a
drop operation on to the target with a rule. We can achieve this using the MVVM pattern too, but we need to take care of the
DataContext property to an ObservableCollection<object> where we can identify which type of data context we are
dropping and apply the rule.
There are some DragDropManagers available in Codeplex and from Telerik.
About Diptimaya Patra
 |
Diptimaya Patra is a Client App Dev MVP, also a software consultant in the following areas: Silverlight, WPF, Expression Blend, Windows Phone 7.
Follow him in tweeter @dpatra
This author has published 13 articles on DotNetSlackers. View other articles or the complete profile here.
|
You might also be interested in the following related blog posts
Silverlight MVP
read more
An alternative to Crystal
read more
Custom Panels in Silverlight/WPF Part 4: Virtualization
read more
.NET RIA Services Part 4: Calling methods on the Server from Silverlight.
read more
Multi-Monitor Support (VS 2010 and .NET 4 Series)
read more
Mixing Silverlight and MS ASP.NET AJAX 3.5 in the same web application.
read more
Getting and setting max zIndex with jQuery
read more
Multi-Item Drag and Drop RadListBox
read more
Telerik Launches RadControls for Silverlight 3 for Line-of-Business Application Development
read more
Winforms Release History : Q2 2009 SP1 (version 2009.2.9.729)
read more
|
|
Please login to rate or to leave a comment.