SOURCE Download:
- Download Filelistview_version_2.zip
- Download Filelistview_version_2_binaries.zip
- Download Filelistview_version_2.1.zip
The project is now maintainedhere: http://fsc.codeplex.com/
Introduction
I was recently asked to add a ' File Tree Pane ' into my editor (https://edi.codeplex.com/discussions/541888) and went Looki ng for a good solution, because the component is really missing and it really bothers me too. The best solution I found, is written by Thomas Willwacher, as usual, here at CodeProject. I really like the concept that Thomas was using and reviewed the project in terms of integrating it in my editor, and while That's still too come, I found already some issues that would probably being difficult to fix in a project this is driven B Y an IoC (which I ' d like to do next).
It is difficult-to-write this-correctly, so does not get me wrong here, I am really grateful that Thomas have posted his Solution. Because I am not even sure whether I could has developed such a nice File Explorer concept to start with. But I saw the architectural issues and I decided to get the this done instead of putting it off. So, here's my take in this solution. I am posting it here in the hope, that it's useful to others, and that we might being able to develop this even further.
Background
The solution presented are about a File Explorer control, can be used in a Tool Window. The user should is able to browse directories, list their files, filter on the listed files, and open files via double CLI CK, drag & Drop and Context menu. The Drag & Drop and Context menu part are not presented here since I does not think this would being hard to add. The solution presented here's just about the same test application, Thomas had posted in his article. I only added a directory browser control and developed the architecture from scratch with MVVM in mind.
Using the Code
The current articles discusses the "code in Filelistview_version2.zip" in the download section. The filelistview_version2.1.zip in the download sections is a refactored version of is currently under development based On my observations and Leung Yat Chun ' s suggestions in the Forum's section.
Re-using the code of the provided solution requires that you reference the Dll assemblies (Filelistview and FolderBrowser) , and copy & parts of the MainWindow.xaml code into your own view implementation. You'll also need the code MainWindow.xaml.cs to create the necessary viewmodels. This is a need to re-use this solution in your own projects.
Points of Interest
The solution presented here contains 4 projects:
- Filelistview, Filelistviewtest and
- FolderBrowser, Testfolderbrowser.
The Filelistview project is the assembly, which contains the meat of the File Explorer controls that this article is Focusin G on. The FolderBrowser project originates from a different codeproject article [2] and is included here since I felt that I di D not need a recent Files selection but a recent Locations selection. So, re-factored this solution, as well, and included the result here.
The ' Test ' projects-Solution contain a demo application that can is executed to check out how things work. The remainder of this article would focus on the Filelistview project and feel free to ask Questions/demand more informatio N If you feel this I should document the FolderBrowser part in more detail.
The views in the Filelistview Project
The Filelistview project is a mainly partitioned in 3 views that's completely separated from each of the other.
Filtercombobox
The Filtercombobox inherits from the ComboBox control [3] and should is fully theme-able since I ' d like to support bright and dark skins. Basically the control where you enter such filter as: ' *.png ', ' *. * ', or (I extended this) ' *.png|*.jpg|*.jpeg '. This filter was then applied to the list of files when the user selects the filter or presses the ENTER key in the text por tion of the ComboBox.
Collapse | Copy Code
<Fview:filtercomboboxDataContext="{Binding Folderview.filters} "ItemsSource="{Binding Currentitems} "SelectedItem="{Binding SelectedItem, updatesourcetrigger=propertychanged} "text= "{Binding CurrentFilter , updatesourcetrigger=propertychanged} "fvbehav: Selectionchangedcommand.changedcommand= "{Binding SelectionChanged} "verticalalignment=" top "horizontalalignment=" Span class= "Code-keyword" >stretch "grid.column=" 3 "margin=" 3 "/>
The above code shows how the Filtercombobox control was implemented in the MainWindow ' s Xaml. A Noteworthy item is the SelectionChangedCommand
behavior [4] which was basically a custom ComboBox behavior that binds itself KeyUp
to the And SelectionChanged
event of the ComboBox. The behavior executes the bound SelectionChanged
command in the Foldercomboboxviewmodel when either event occurs. This on turn executes the SelectionChanged_Executed
method which evaluates whether the currently entered path refers to a valid directory or n Ot. The method raises the Oncurrentpathchanged event of the FolderChangedEventArgs
type if the entered path is in fact in existence. This event was received by another ViewModel discussed further below.
Foldercombobox
The Foldercombobox control is the ComboBox, keeps the list of folders that a user can select as the base of his explor ation. This includes the usual suspects, such as, Desktop, My Documents, and Drives but also contains a list of recent Locations:
The Foldercombobox makes also use of the selectionchanged behavior discussed above. It is very similar to the Filtercombobox except for 2 additions:
Collapse | Copy Code
<SetterProperty="ItemTemplate "><Setter.value><DataTemplateDataType="{x:type VM:FSITEMVM} "><GridToolTip="{Binding FullPath} "Tooltipservice.isenabled="{Binding Showtooltip} "><Grid.columndefinitions><ColumnDefinitionWidth="{Binding Indentation} "/><ColumnDefinitionWidth="20 "/><ColumnDefinitionWidth="100 "/></Grid.columndefinitions><Grid.rowdefinitions><RowDefinition/></Grid.rowdefinitions><ImageGrid.Row="0 "Grid.column="1 "Source="{Binding Path=displayicon} "Width="16 "Height="16 "/><TextBlockGrid.Row="0 "grid.column= "2" text=" {binding DisplayName} "/> </grid> < /datatemplate> </Setter.Value></ Setter>
This ItemTemplate shows tha items display in the Drop-down sections of the ComboBox consist of an Image and a TextBlock. The ItemTemplate binds to instances of the ITEMVM type which are part of the ObservableCollection<FSItemVM> CurrentItems
collection in the Foldercomboboxviewmodel .
Collapse | Copy Code
<SetterProperty="Itemcontainerstyle "><Setter.value><StyleTargetType="{x:type ComboBoxItem} "BasedOn="{StaticResource {x:type ComboBoxItem}} "> <Style.Triggers> <datatrigger binding="{Binding} "value="{x:null} "> <setter property="IsEnabled "value="False "/> <setter property="Template "> <Setter.Value> <controltemplate targettype="{x:type ComboBoxItem} "> <separator width="0 "height="Ten "/></ControlTemplate></Setter.value> </setter> < /datatrigger> </Style.Triggers> </ style> </setter.value></setter>
The 2nd interesting thing in the Foldercombobox control is the ItemContainerStyle
which includes a then DataTrigger
inserts a when the Seperator
Boun D value is null
. The above Xaml literally converts a value of NULL into a seperator entry in the drop list. This little trick inserts a seperator in the Drop-down list that allows us to group items such that users cannot click int o The extra space (since seperators is not hit test visible).
Flistview
The Flistview is basically an out of the box ListView with an attached behavior addition that converts a double click into A bound doubleclickcommand in the Filelistviewviewmodel [5].
The ViewModels in the Filelistview Project
This solution includes a few more viewmodels than the original version 1. There is basically 1 viewmodel for each of the three controls documented in the previous section. The Foldercomboboxviewmodel and the Filelistviewmodel make use of the FSITEMVM class to manage their file specific collect Ions. TheFolderlistviewmodel is the heart of the solution since it instantiates the other control specific viewmodels a ND manages their events when they say, hey:
- ... just selected a new Folder
(Oncurrentpathchanged in Foldercomboboxviewmodel and Filelistviewmodel)
- ... just selected a new Filter (onfilterchanged in Filtercomboboxviewmodel)
- ... just want to open a file (OnFileOpen in Filelistviewmodel)
Conclusions
Converting this project took me about 3-4 days of work but I think it is worth it since I have a much clearer understandi Ng now and feel motivated to add other toys such as an async query and load of the Filelistview. This could include a stop button shown in the Folder or Filter combobox to stop process which may take extra ordinary long When accessing slow devices.
Over all I has learned a few more tricks looking deep into someone else's code, so I am once again grateful for being par T of this community. And now I am looking forward to see what the community thinks about this.
Credits
The Class diagrams in this article were drawn with #Develop (http://www.icsharpcode.net/opensource/sd/). I would like to say thank-the original article and code version and the tips from Leung Yat Chun here at Code proj Ect.
References
- [1] a wpf file ListView and ComboBox (Version I) by Thomas WILLW Acher
Http://www.codeproject.com/articles/167873/a- Wpf-file-listview-and-combobox
- [2] wpf folder Browser by Erik Rude
Http://www.codeproject.com/articles/352874/ Wpf-folder-browser
- [3] Inheriting from a look Less WPF control
http://www.codeproject.com/articles/575645/inheriting-from-a-look-less- wpf-control
- [4] Patterns in attached behaviors
http://www.codeproject.com/Articles/422537/ Patterns-in-attached-behaviours
- [5] attachedcommandbehavior V2 aka ACB
http://marlongrech.wordpress.com /2008/12/13/attachedcommandbehavior-v2-aka-acb/
A WPF File ListView and ComboBox