1
votes

I want to make a WPF ListBox photo album for one my college projects.

I need to design a DataTemplate/ListBox style so it will look like a stack jumbled of photos, i.e., the top one being the item in focus/selected (see diagram below).

Image here

alt text

With reference to the drawing,

  • item 1) is not shown
  • item 2) is at the back of stack
  • item 3) in the middle of 2 and 4
  • item 4) is in focus
  • item 5) is not shown

I am having the most trouble getting the items to rotate and overlap and the most difficult task is getting the item in focus to be shown on top.

I'm using Visual Basic because I haven't yet mastered C# so it would be useful if examples could be in VB or use mainly WPF.

1

1 Answers

0
votes

To get the items to rotate, you should look at using Transforms. The one that is most relevant in this case is the Rotate Transform, also to give it that random scattered apperance, we can use an ObjectDataProvider and generate our angles somewhere else.

I don't know VB, but the only C# involved in this is pretty simple, and should be easily transferable.

Lets just use something simple like Colors, which can easily be switched over to image resource paths. Here we've got an ObservableCollection of our Colors, and also a separate class that we will use to generate angles, all it's going to do is return a number between 0 and 360, which we will use to rotate each item.

public partial class Window1 : Window
{
    public Window1()
    {
        InitializeComponent();

        Colors = new ObservableCollection<string>();
        Colors.Add("Red");
        Colors.Add("Blue");
        Colors.Add("Green");
        Colors.Add("Yellow");

        this.DataContext = this;
    }

    public ObservableCollection<string> Colors
    {
        get;
        set;
    }
}

public class AngleService
{
    private static Random rand = new Random();

    public int GetAngle()
    {
        return rand.Next(0, 90);
    }
}

In the XAML, we can now create a resource that can be used to generate the angles.

<Window.Resources>
    <local:AngleService x:Key="Local_AngleService" />
    <ObjectDataProvider x:Key="Local_AngleProvider"
                        x:Shared="False"
                        ObjectInstance="{StaticResource Local_AngleService}"
                        MethodName="GetAngle" />
</Window.Resources>

Now, we just need to create something to display our items. We can put them in a ListBox and add a data template to set the background for each color item, as well as apply the RotateTransform.

<ListBox ItemsSource="{Binding Colors}"
         VerticalContentAlignment="Center"
         HorizontalContentAlignment="Center">
    <ListBox.ItemTemplate>
        <DataTemplate>
            <Border x:Name="uiItemBorder"
                    BorderBrush="Black"
                    BorderThickness="2"
                    CornerRadius="3"
                    Background="{Binding}"
                    Width="50"
                    Height="50">
                <TextBlock Text="{Binding}"
                           VerticalAlignment="Center"
                           HorizontalAlignment="Center" />
                <Border.RenderTransform>
                    <RotateTransform Angle="{Binding Source={StaticResource Local_AngleProvider}}" />
                </Border.RenderTransform>
            </Border>
        </DataTemplate>
    </ListBox.ItemTemplate>
</ListBox>

The UI still needs a bit of work from there, but that should help out with the rotation of the items.