用TreeView和DataList控件創建一個在線圖片庫

本文英文原版與代碼下載:
http://aspnet.4guysfromrolla.com/articles/083006-1.aspx

用TreeView和DataList控件創建一個在線圖片庫


導言:

ASP.NET 2.0包含了很多的Web控件,比如TreeView。它被設計來顯示具有層次結構的數據。TreeView可以綁定到一個層次結構數據源,比如XmlDataSource 或 SiteMapDataSource,當然也可以編程來構建.對於用TreeView綁定到SiteMapDataSource以展示一個網站地圖的示例,可參見系列文章《Examining ASP.NET 2.0's Site Navigation》(http://aspnet.4guysfromrolla.com/articles/111605-1.aspx)

     常見的層次結構數據是web server的文件系統file system.在很多情況下,可能有某個文件夾,裏面包含了我們要瀏覽的很多文件以及次級文件夾.通過命名空間System.IO裏的類, 我們可以通過編程來用website的目錄體系來填充TreeView控件,當用戶點擊一個文件夾時,就顯示該文件夾下的文件.

      

                                                               圖1


在本文,我們將考察如何創建一個簡單的圖片展示頁面.我們將用到2個控件:TreeView,它用來展示文件體系;而DataList控件用來展示某個文件夾裏的圖片.

Displaying the TreeView

在本示例,我們將創建2個部分:

.一個TreeView控件:列出某個指定節點下的文件夾
.一個data Web控件:用於列出某個選定文件夾下的文件.就本文而言,我們使用的是DataList,不過在某些情況下,可能用GridView, DetailsView, FormView,Repeater控件可能更好一些.

   讓我們開始編程創建TreeView.對ASP.NET 2.0 TreeView的數據,我們可以“顯式”(通過一個XmlDataSource 或 SiteMapDataSource)或通過編程來賦值.由於沒有內置的返回目錄信息的控件可利用,因此我們需要通過編程對TreeView綁定數據.具體來說,我們需要獲取某個根目錄的信息,接下來纔是次級目錄.對包含的文件夾,向TreeView添加一個TreeNode節點.

   .NET Framework包含了很多的類來處理file system;這些類都包含在System.IO命名空間裏.比如類DirectoryInfo, 它包含返回指定目錄的子目錄的方法(GetDirectories()),當然還有返回指定目錄下所有文件的方法(GetFiles()).

   如下的代碼裏,我們用某個根目錄下的文件層次結構對ID爲PictureTree的TreeView控件進行填充,而根目錄由常量VirtualImageRoot來指定.代碼裏使用的AddNodeAndDescendents方法對文件體系進行遞歸操作(recurse)(對遞歸的更多詳情,請參閱我以前的文章《Recursion, Why It's Cool》(http://www.4guysfromrolla.com/webtech/060299-2.shtml))

Private Const VirtualImageRoot = "~/Images/Public/"
Private Sub PopulateTree()
    'Populate the tree based on the subfolders of the specified VirtualImageRoot
    Dim rootFolder As New DirectoryInfo(Server.MapPath(VirtualImageRoot))
    Dim root As TreeNode = AddNodeAndDescendents(rootFolder, Nothing)

    'Add the root to the TreeView
    PictureTree.Nodes.Add(root)
End Sub

Private Function AddNodeAndDescendents(ByVal folder As DirectoryInfo, ByVal parentNode As

TreeNode) As TreeNode
    'Add the TreeNode, displaying the folder's name and storing the full path to the folder as

the value...
    Dim virtualFolderPath As String
    If parentNode Is Nothing Then
        virtualFolderPath = VirtualImageRoot
    Else
        virtualFolderPath = parentNode.Value & folder.Name & "/"
    End If

    Dim node As New TreeNode(folder.Name, virtualFolderPath)

    'Recurse through this folder's subfolders
    Dim subFolders As DirectoryInfo() = folder.GetDirectories()
    For Each subFolder As DirectoryInfo In subFolders
        Dim child As TreeNode = AddNodeAndDescendents(subFolder, node)
        node.ChildNodes.Add(child)
    Next

    Return node     'Return the new TreeNode
End Function

每個節點都被賦予了一個display value值和一個hidden value值.該display value值是在樹形結構裏要顯示出來的;而hidden value值是要貫穿postbacks,並與該節點的額外信息有所關聯的值.這2個值在TreeNode構造函數裏指定的——Dim node As New TreeNode(text, value). 其text就是文件夾的名稱,而value就是文件夾的相對路徑(virtual path).比如-/Images/Public/Picture1.jpg.當然,相對於物理路徑(physical path),該相對路徑可能就變成了C:/MySites/ImageGallery/Images/Public/Picture1.jpg. 關於virtual paths 和 physical paths的區別以及如何將virtual paths轉換成physical paths的更多信息請看文章《Using Server.MapPath》(http://www.4guysfromrolla.com/webtech/121799-1.shtml)

顯示選定文件夾裏的文件

在TreeView裏顯示文件系統體系之後,剩下的事情就是顯示選定文件夾裏的文件.爲此,我們要在頁面裏添加一個data Web控件,將其綁定到當前選定文件夾裏的文件列表.但是我們如何才知道哪個文件夾被選中了,以及怎麼知道用戶什麼時候想查看另一個文件夾裏的文件呢?

TreeView有一個SelectedValue屬性,它返回當前選中節點的value,記得我們已經將文件夾的相對路徑賦值給相應節點的value.有了選定文件夾的路徑,要獲取該文件夾裏的文件列表,我們可以創建一個DirectoryInfo object對象,並使用其GetFiles()方法,該方法返回一批FileInfo objects對象,然後將其綁定到data Web控件(就本文而言,我們使用一個DataList控件).

當點擊TreeView的一個節點時,接着將發生一個postback,並觸發TreeView的 SelectedNodeChanged event事件.此時,我們將剛選定的文件夾裏的數據重新綁定到data Web控件裏.

上述功能可以用下面的代碼來實現.DisplayPicturesInFolder(virtualFolderPath)方法獲取指定文件夾裏的文件,並將其綁定到ID爲PicturesInFolder的DataList控件裏.而SelectedNodeChanged事件處理器僅僅簡單的調用DisplayPicturesInFolder(virtualFolderPath)方法,傳入選定節點的value值.

Protected Sub PictureTree_SelectedNodeChanged(ByVal sender As Object, ByVal e As

System.EventArgs) Handles PictureTree.SelectedNodeChanged
    'Refresh the DataList whenever a new node is selected
    DisplayPicturesInFolder(PictureTree.SelectedValue)
End Sub

Private Sub DisplayPicturesInFolder(ByVal virtualFolderPath As String)
    'Security check: make sure folderPath starts with VirtualImageRoot and doesn't include any

".."
    If Not virtualFolderPath.StartsWith(VirtualImageRoot) OrElse virtualFolderPath.IndexOf("..")

>= 0 Then
        Throw New ApplicationException("Attempting to view a folder outside of the public image

folder!")
    End If

    'Get information about the files in the specified folder
    Dim folder As New DirectoryInfo(Server.MapPath(virtualFolderPath))
    Dim fileList As FileInfo() = folder.GetFiles()

    PicturesInFolder.DataSource = fileList
    PicturesInFolder.DataBind()
End Sub 

注意:
DisplayPicturesInFolder(virtualFolderPath)方法裏的第一行代碼首先做了一個檢查,確保被請求的路徑位於常量VirtualImageRoot指定的根目錄下.

ID爲PicturesInFolder的DataList控件只包含了一個ItemTemplate模板,該模板顯示了圖片的名字(沒有包含文件擴展名),幷包含一個Image Web控件來展示該圖片:

<asp:DataList ID="PicturesInFolder" runat="server" Width="100%" CellPadding="5">
    <ItemTemplate>
        <h3><asp:Label runat="server" ID="FileNameLabel" Text='<%#

System.IO.Path.GetFilenameWithoutExtension(Eval("Name")) %>'></asp:Label></h3>
       
        <asp:Image runat="server" ID="Picture" ImageUrl='<%# PictureTree.SelectedValue & Eval

("Name").ToString() %>' />
        <br /><br />
    </ItemTemplate>
    <AlternatingItemStyle BackColor="#E0E0E0" />
</asp:DataList> 

最終的效果是一個簡單的圖片管理程序。TreeView控件列出了文件系統裏某個根目錄下的子文件夾,點擊某個具體的文件夾,其包含的圖片將顯示在右邊.在web server裏上載,編輯或刪除image文件,該程序立馬就能反映出這些改動!

               
                                                                      圖2


                                                         圖3

祝編程快樂! 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章