tags:

views:

2673

answers:

4

How would you implement a GUI similar to the "My Computer" view in Windows Explorer?

In particular the "Icons" view mode. Including the grouping of different item types (as Files Stored on This Computer/Hard Disk Drives/Devices with Removable Storage groups in Windows Explorer)

In WinForms I would use a ListView for this thing but in WPF the only thing that has even come close is a listbox with a custom ControlTemplate but it seems like too much effort!

+2  A: 

Have a TreeView with HeirarchichalDataTemplate defined for your FileSystem class

Jobi Joy
A: 

Too much effort indeed. A quick way to use a ListView control is through the WPF interoperability. Create a WindowsFormsHost element, and add your listview to that.
Read more here: http://msdn.microsoft.com/en-us/library/ms742474.aspx

Matt Brunell
Honestly, what's the point of using WPF, then?
Bob King
A: 

See FolderView, FileView, etc controls from Shell MegaPack.WPF

It supports grouping and icons mode (among lots of other things).

+1  A: 

It is a lot of typing (~50 lines) but when you finish the basic functionality you can easily do things like change the item display or add expand/collapse functionality for the groups, here is an example (with expand/collapse, just for fun):

First our data objects:

public class Item
{
    public string Type { get; set; }
    public string Name { get; set; }
    public ImageSource Icon { get; set; }
}

Create them in your code and set a list of them as the DataContext of the following window:

<Window x:Class="ListViewTest.Window1"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="Window1" Height="300" Width="300" Name="W">
    <Window.Resources>
        <CollectionViewSource x:Key="Items" Source="{Binding}">
            <CollectionViewSource.GroupDescriptions>
                <PropertyGroupDescription PropertyName="Type"/>
            </CollectionViewSource.GroupDescriptions>
        </CollectionViewSource>
        <DataTemplate x:Key="ItemTemplate">
            <Grid Width="128">
                <Grid.RowDefinitions>
                    <RowDefinition Height="40"/>
                    <RowDefinition Height="12"/>
                </Grid.RowDefinitions>
                <Image Source="{Binding Icon}"/>
                <TextBlock Text="{Binding Name}" Grid.Row="1"/>
            </Grid>
        </DataTemplate>
        <ItemsPanelTemplate x:Key="ItemPanel">
            <WrapPanel Orientation="Horizontal" Width="{Binding ElementName=W, Path=ActualWidth}"/>
        </ItemsPanelTemplate>
        <DataTemplate x:Key="HeaderTemplate">
            <StackPanel Margin="0 15">
                <TextBlock Text="{Binding Name}"/>
                <Rectangle Height="1" Fill="Blue"/>
            </StackPanel>
        </DataTemplate>
        <Style x:Key="ContainerStyle" TargetType="{x:Type GroupItem}">
            <Setter Property="Template">
                <Setter.Value>
                    <ControlTemplate>
                        <Expander Header="{Binding Name}" IsExpanded="True">
                            <ItemsPresenter/>
                        </Expander>
                    </ControlTemplate>
                </Setter.Value>
            </Setter>
        </Style>
    </Window.Resources>

    <Grid>
        <ListBox 
            ItemsSource="{Binding Source={StaticResource Items}}"
            ItemTemplate="{StaticResource ItemTemplate}"
            ItemsPanel="{StaticResource ItemPanel}">
            <ListBox.GroupStyle>
                <GroupStyle 
                    HeaderTemplate="{StaticResource HeaderTemplate}"
                    ContainerStyle="{StaticResource ContainerStyle}"/>
            </ListBox.GroupStyle>
        </ListBox>
    </Grid>
</Window>

There may be some bugs in there but its a good start.

Nir