Пошаговое руководство. Иерархические данные в элементе управления TreeView

Visual Studio 2010

Обновлен: Ноябрь 2007

Элемент управления ASP TreeView используется для отображения данных в иерархической структуре. Пользователи могут открывать отдельные узлы, которые в свою очередь содержат дочерние узлы. Элемент управления TreeView используется для отображения данных XML, но его также можно применять для любых данных, которые можно представить иерархически. В данном пошаговом руководстве представлены основы использования элемента управления TreeView и различные методы отображения иерархических данных.

В данном пошаговом руководстве, в частности, рассматриваются следующие задачи:

  • Использование элемента управления TreeView для отображения данных XML.

  • Настройка отображения элемента управления TreeView.

  • Отображение записей из связанных таблиц базы данных в элементе управления TreeView.

Для выполнения этого пошагового руководства потребуются следующие компоненты:

  • Microsoft Visual Web Developer (Visual Studio).

  • Компоненты доступа к данным MDAC версии 2.7 или более поздней версии.

    Если используется Microsoft Windows XP или Windows Server 2003, то компоненты MDAC 2.7 уже установлены. Однако если используется Microsoft Windows 2000, то может потребоваться обновление компонентов доступа к данным MDAC, уже установленных на компьютере. Дополнительные сведения содержатся в разделе «Установка компонентов доступа к данным MDAC» в библиотеке MSDN.

  • Доступ к базе данных «Northwind» на SQL Server. Сведения о загрузке и установке учебной базы данных «Northwind» SQL Server см. в документе Установка образцов баз данных на веб-узле Microsoft SQL Server.

    7a9swst5.alert_note(ru-ru,VS.100).gifПримечание.

    Получите сведения о входе в систему SQL Server у администратора сервера.

  • Имя пользователя и пароль для учетной записи SQL Server, предоставляющие доступ к базе данных «Борей», если база данных SQL Server расположена не на веб-сервере.

Создайте новый веб-узел и страницу, выполнив следующие действия.

Создание веб-узла на базе файловой системы

  1. Откройте Visual Web Developer.

  2. В меню Файл выберите пункт Создать и выберите Веб-узел. При использовании Visual Web Developer, экспресс-выпуск в меню Файл выберите СоздатьВеб-узел.

    Откроется диалоговое окно Создать веб-узел.

  3. В группе Установленные шаблоны Visual Studio выберите Веб-узел ASP.NET.

  4. В поле Расположение выберите Файловая система и введите имя папки, в которой будут храниться страницы веб-узла.

    Например, введите имя папки C:\WebSites\HierarchicalData.

  5. В списке Язык выберите предпочтитаемый язык программирования.

  6. Нажмите кнопку ОК.

    Visual Web Developer создаст папку и новую страницу с именем Default.aspx.

Создайте новый XML-файл, выполнив следующие действия.

Создание XML-файла

  1. В обозревателе решений щелкните правой кнопкой мыши веб-узел и нажмите кнопку Добавить новый элемент.

  2. В диалоговом окне Добавить новый элемент в Стандартныешаблоны выберите XML-файл.

  3. В поле Имя введите Bookstore.xml и нажмите кнопку Добавить.

    Visual Web Developer создаст файл Bookstore.xml и откроет редактор кода.

  4. Скопируйте приведенные ниже данные XML и вставьте их в файл Bookstore.xml поверх имеющегося там содержимого.

    <?xml version="1.0" standalone="yes"?>
    <bookstore>
      <genre name="fiction">
        <book ISBN="10-000000-001">
          <title>The Iliad and The Odyssey</title>
          <price>12.95</price>
          <comments>
            <userComment rating="4">
               Best translation I've read.
            </userComment>
            <userComment rating="2">
               I like other versions better.
            </userComment>
          </comments>
        </book>
        <book ISBN="10-000000-999">
          <title>Anthology of World Literature</title>
          <price>24.95</price>
          <comments>
            <userComment rating="3">
              Needs more modern literature.
            </userComment>
            <userComment rating="4">
              Excellent overview of world literature.
            </userComment>
          </comments>
        </book>
      </genre>
      <genre name="nonfiction">
        <book ISBN="11-000000-002">
          <title>Computer Dictionary</title>
          <price>24.95</price>
          <comments>
            <userComment rating="3">A valuable resource.</userComment>
          </comments>
        </book>
        <book ISBN="11-000000-003">
          <title>Cooking on a Budget</title>
          <price>23.95</price>
          <comments>
            <userComment rating="4">Delicious!</userComment>
          </comments>
        </book>
      </genre>
    </bookstore>
    

    XML-файл содержит сведения о книгах, которые можно приобрести в книжном Интернет-магазине.

  5. Сохраните файл Bookstore.xml и закройте его.

В этом разделе показано, как использовать элемент управления TreeView для отображения данных XML. Для начала можно вывести данные XML без какой-либо специальной конфигурации.

Отображение данных XML

  1. Откройте страницу Default.aspx и переключитесь в режим конструктора.

  2. Из панели элементов, группы Навигация, перетащите на страницу элемент управления TreeView.

  3. Щелкните правой кнопкой мыши элемент управления TreeView, а затем выберите команду Показать смарт-тег.

  4. В меню Задачи TreeView в раскрывающемся списке Выбор источника данных выберите пункт Новый источник данных. Запустится Мастер настройки источников данных.

  5. В окне Источник данных для приложения выберите XML-файл. Оставьте идентификатор источника данных по умолчанию. Нажмите кнопку ОК.

  6. В диалоговом окне Настройка источника данных в поле Файл данных введите ~/Bookstore.xml и нажмите кнопку ОК.

Теперь можно проверить страницу.

Тестирование страницы

  1. Нажмите клавиши CTRL+F5 для запуска страницы.

  2. Сверните и разверните узлы элемента управления.

    По умолчанию узлы отображают только имена тегов элементов файла Bookstore.xml.

Можно настроить данные, отображаемые в элементе управления TreeView, создав пользовательские привязки, позволяющие указать данные XML-файла, отображаемые в каждом узле.

Создание пользовательских привязок

  1. На странице Default.aspx щелкните правой кнопкой мыши элемент управления TreeView, а затем выберите команду Показать смарт-тег.

  2. В меню Задачи TreeView выберите команду Изменить привязку данных TreeNode.

    Появится диалоговое окно Редактор привязок данных TreeView.

  3. Снимите флажок Автоматическое создание привязки данных, так как привязки определяются далее.

  4. Нажмите кнопку Добавить, чтобы создать новую привязку, и затем в области Свойства привязки данных, присвойте свойству DataMember значение bookstore, а свойству Text присвойте значение Book Information.

    Используется настройка отображения статического значения, потому что узел Bookstore является самым верхним узлом XML-файла и отображается только в элементе управления TreeView.

  5. Нажмите кнопку Добавить для создания второй привязки и затем в области Свойства привязки данных присвойте свойству DataMember значение genre, а свойству TextField присвойте значение name.

    Это приведет к тому, что узел будет считывать элемент <genre> XML-файла и присвоит значение атрибута name свойству TextField.

  6. Нажмите кнопку Добавить для создания второй привязки и затем в области Свойства привязки данных присвойте свойству DataMember значение book, свойству TextField присвойте значение ISBN.

  7. Нажмите кнопку ОК.

Теперь можно протестировать страницу.

Тестирование страницы

  • Нажмите клавиши CTRL+F5 для запуска страницы.

    На этот раз элемент управления TreeView отображает три уровня, соответствующие заданным привязкам. Три уровня включают корневой узел Book Information, группы жанра и сведения ISBN.

Можно создать привязки к данным для всех элементов XML-файла, но привязку можно выполнять только к атрибутам элемента, внутреннему тексту, имени элемента и значению элемента. Нельзя выполнять привязку к вложенным элементам. Для отображения элементов во вложенных элементах создаются отдельные привязки к этим элементам. Также можно преобразовать XML-файл при помощи XSLT, чтобы преобразовать все элементы в атрибуты. Дополнительные сведения и пример см. в описании свойства XmlDataSource.TransformFile.

Элемент управления TreeView может отображать любые типы иерархических данных, даже если данные логические, как в базах данных, а не физические, как в XML-файле. В этом примере элемент управления TreeView используется для отображения данных из связанных таблиц базы данных «Борей».

Сначала создайте подключение к компьютеру, на котором запущен сервер SQL Server, содержащий базу данных «Борей».

Чтобы создать подключение к SQL Server

  1. В обозревателе серверов щелкните правой кнопкой мыши Подключения данных, а затем Добавить подключение. При использовании Visual Web Developer, экспресс-выпуск используйте обозреватель баз данных.

    Открывается диалоговое окно Добавить подключение.

    • Если в списке Источник данных отсутствует элемент Microsoft SQL Server (SqlClient), нажмите кнопку Изменить и в диалоговом окне Выбор источника данных выберите Microsoft SQL Server.

    • При отображении страницы Выбор источника данных в списке Источник данных выберите тип используемого источника данных. В этом пошаговом руководстве в качестве типа источника данных используется Microsoft SQL Server. В списке Поставщик данных выберите Поставщик данных платформы .NET Framework для SQL Server и нажмите кнопку Продолжить.

    7a9swst5.alert_note(ru-ru,VS.100).gifПримечание.

    Если вкладка «Обозреватель серверов» не видна в Visual Web Developer, то в меню Вид щелкните Обозреватель серверов. Если вкладка «Обозреватель баз данных» не видна, то в меню Вид щелкните Обозреватель баз данных.

  2. В поле Добавить подключение введите имя сервера в поле Имя сервера.

  3. Для раздела Вход на сервер выберите параметр, который подходит для доступа к запущенной базе данных SQL Server (встроенная безопасность или определенный идентификатор и пароль) и при необходимости введите имя пользователя и пароль.

  4. Установите флажок Сохранить пароль.

    7a9swst5.alert_note(ru-ru,VS.100).gifПримечание.

    В производственных приложениях не следует использовать Сохранить пароль, так как при этом имя пользователя и пароль встраиваются в файлы приложения.

  5. В разделе Выберите или введите имя базы данных введите Northwind.

  6. Нажмите кнопку Проверить подключение и, убедившись в его наличии, нажмите кнопку ОК.

    Новое подключение будет создано в Подключения данных в обозревателе серверов (или обозревателе баз данных).

Настройка элемента управления TreeView для отображения содержимого баз данных

В этом разделе рассматривается заполнение узлов данными. Узлы первого уровня представляют основные данные, в этом случае — категории. Если пользователь щелкает узел, при помощи запроса базы данных, запрашивающего продукты категории, создаются дочерние узлы этой категории. Для извлечения данных можно использовать элемент управления источника данных. Однако в этом пошаговом руководстве описывается создание и выполнение запроса программными средствами.

Сначала создайте новую страницу и элемент управления TreeView.

Создание страницы и элемента управления TreeView

  1. Добавьте веб-страницу ASP.NET (страницу Web Forms) с именем TreeViewDynamic.aspx к веб-узлу.

  2. Откройте страницу TreeViewDynamic.aspx page, перейдите в режим конструктора, перетащите на страницу из Toolbox, группы Стандартные, элемент управления Label и назовите его labelStatus.

    Элемент управления labelStatus используется только для сообщений об ошибках.

  3. Из панели элементов, группы Навигация, перетащите на страницу элемент управления TreeView.

  4. Щелкните правой кнопкой мыши элемент управления TreeView, выберите Свойства, а затем присвойте свойству MaxDataBindDepth значение 2.

  5. Щелкните правой кнопкой мыши элемент управления TreeView, выберите пункт Показать команды смарт-тегов, а затем в меню Задачи TreeView щелкните пункт Правка узлов.

  6. В диалоговом окне Редактор узлов TreeView щелкните значок с именем Добавить корневой узел, затем в области Свойства присвойте свойству Text значение Список продуктов, а свойству PopulateOnDemand присвойте значение true.

  7. Нажмите кнопку .

    При этом создается самый верхний узел дерева, содержащий только статичный текст.

Настройка файла Web.config

  1. Из группы Данные в панели элементов перетащите на страницу элемент управления SqlDataSource.

  2. Выберите элемент управления SqlDataSource и затем щелкните команду Показать смарт-тег.

  3. В меню SqlDataSource выберите команду Настройка источника данных.

    Мастер Настройка источника данных – SqlDataSource1 отобразит страницу, в которой можно выбрать подключение.

  4. В поле Какое подключение ваше приложение должно использовать для работы с базой данных? введите подключение, созданное на шаге «Создание подключения к SQLServer» и щелкните Далее.

    Мастер отображает страницу, на которой вы можете сохранить строку соединения в файле конфигурации. Сохранение строки подключения в файле конфигурации имеет два преимущества.

    • Это более безопасно, чем сохранение ее на странице.

    • Можно использовать одну строку подключения на нескольких страницах.

  5. Установите флажок Да, сохранить подключение как и нажмите кнопку Далее.

    Мастер отобразит страницу, на которой можно указать, какие данные требуется извлечь из базы данных.

  6. В группе Укажите столбцы из таблицы или представления в поле Имя щелкните Категории.

  7. В группе Столбцы выберите поля CategoryID и CategoryName.

  8. Нажмите кнопку Далее.

  9. Нажмите кнопку Готово.

    Строка подключения, созданная в файле Web.config, используется позже в методе RunQuery, определенном далее в этом руководстве. Элемент управления SqlDataSource не используется.

Теперь добавляется код, реализующий заполнение дочерних узлов элемента управления, если пользователь щелкает узел. Для динамического добавления узлов создается обработчик событий TreeNodePopulate.

Создание обработчика событий

  1. Щелкните правой кнопкой мыши элемент управления TreeView и в группе Свойства щелкните значок События.

  2. Дважды щелкните поле события TreeNodePopulate.

    Visual Web Developer переключится в режим представления исходного кода.

  3. В обработчик событий добавьте нижеприведенный выделенный код.

    Protected Sub TreeView1_TreeNodePopulate(ByVal sender As Object, _
    ByVal e As System.Web.UI.WebControls.TreeNodeEventArgs) _
    Handles TreeView1.TreeNodePopulate
        If e.Node.ChildNodes.Count = 0 Then
            Select Case e.Node.Depth
                Case 0
                    PopulateCategories(e.Node)
                Case 1
                    PopulateProducts(e.Node)
            End Select
        End If
    End Sub
    

    protected void TreeView1_TreeNodePopulate(
        object sender, TreeNodeEventArgs e)
    {
        if (e.Node.ChildNodes.Count == 0)
        {
            switch (e.Node.Depth)
            {
                case 0:
                    PopulateCategories(e.Node);
                    break;
                case 1:
                    PopulateProducts(e.Node);
                    break;
            }
        }
    }
    

    Этот код вызывается, если пользователь щелкает узел, чтобы открыть его. Так как необходимо отображать различные данные на разных уровнях дерева, следует определить глубину выбранного узла и заполнить узлы на этом уровне. В этом руководстве метод PopulateCategories вызывается, если пользователь щелкает корневой узел (глубина 0). Метод PopulateProducts вызывается, если пользователь щелкает имя категории (глубина 1). Эти методы представлены в следующем разделе.

    Объект TreeNodeEventArgs предоставляет программный доступ к текущему узлу. Для заполнения узла в него следует добавить элементы. В примере кода узел передается методу, который добавляет дочерние узлы.

Считывание данных узла из базы данных

Данные, отображаемые в каждом узле, поступают из базы данных. Необходимо написать код, выполняющий запрос базы данных, считывающий записи и создающий узел для каждой из них. В этом руководстве предполагается, что применяется пример базы данных SQL Server «Борей», поэтому следует использовать объекты ADO.NET из пространства имен System.Data.SqlClient.

Для узлов первого уровня (уровень 0) отображается список всех доступных категорий. Написанный код вызывает метод RunQuery, который создается далее.

Добавление узлов для всех категорий

  1. Перейдите в представление Исходный код.

  2. При работе со страницей в одном файле добавьте следующие директивы в верхнюю часть страницы кода.

    <%@ Import Namespace="System.Data" %>
    <%@ Import Namespace="System.Data.SqlClient" %>
    

    Импорт пространств имен облегчит написание кода.

  3. При работе со страницей с выделенным кодом перейдите на эту страницу (TreeViewDynamic.aspx.vb или TreeViewDynamic.aspx.cs) и добавьте следующие строки в верхнюю часть файла кода за пределами объявления классов.

    Imports System.Data
    Imports System.Data.SqlClient
    

    using System.Data;
    using System.Data.SqlClient;
    
  4. Убедитесь, что страница открыта в режиме представления исходного кода.

  5. Добавьте следующий метод в страницу кода.

    Sub PopulateCategories(ByVal node As TreeNode)
        Dim sqlQuery As New SqlCommand( _
            "Select CategoryName, CategoryID From Categories")
        Dim ResultSet As DataSet
        ResultSet = RunQuery(sqlQuery)
        If ResultSet.Tables.Count > 0 Then
            Dim row As DataRow
            For Each row In ResultSet.Tables(0).Rows
                Dim NewNode As TreeNode = New _
                    TreeNode(row("CategoryName").ToString(), _
                    row("CategoryID").ToString())
                NewNode.PopulateOnDemand = True
                NewNode.SelectAction = TreeNodeSelectAction.Expand
                node.ChildNodes.Add(NewNode)
            Next
        End If
    End Sub
    

    void PopulateCategories(TreeNode node)
    {
        SqlCommand sqlQuery = new SqlCommand(
            "Select CategoryName, CategoryID From Categories");
        DataSet resultSet;
        resultSet = RunQuery(sqlQuery);
        if (resultSet.Tables.Count > 0)
        {
            foreach (DataRow row in resultSet.Tables[0].Rows)
            {
                TreeNode NewNode = new
                    TreeNode(row["CategoryName"].ToString(),
                    row["CategoryID"].ToString());
                NewNode.PopulateOnDemand = true;
                NewNode.SelectAction = TreeNodeSelectAction.Expand;
                node.ChildNodes.Add(NewNode);
            }
        }
    }
    

    В коде создается объект SqlCommand, инкапсулирующий текст запроса. Он передает объект методу (который создается разработчиком), выполняющему запрос базы данных и возвращающему объект DataSet. Затем код в цикле проходит по записям объекта DataSet и создает узел для каждой записи, записывая в текст и значение узла содержимое базы данных. Затем свойству PopulateOnDemand каждого узла присваивается значение true, чтобы узел вызывал событие TreeNodePopulate, когда пользователь щелкает его. СвойствоSelectAction задано таким образом, что узлы по умолчанию разворачиваются.

Во втором уровне узлов отображаются продукты каждой категории. Поэтому для заполнения узлов продуктов требуется параметризованный запрос, чтобы можно было извлечь продукты текущей категории и соответствующим образом заполнять дочерние узлы.

Добавление узлов продуктов

  • Добавьте следующий метод в страницу кода.

    Sub PopulateProducts(ByVal node As TreeNode)
        Dim sqlQuery As New SqlCommand
        sqlQuery.CommandText = "Select ProductName From Products " & _
            " Where CategoryID = @categoryid"
        sqlQuery.Parameters.Add("@categoryid", SqlDbType.Int).Value = _
            node.Value
        Dim ResultSet As DataSet = RunQuery(sqlQuery)
        If ResultSet.Tables.Count > 0 Then
            Dim row As DataRow
            For Each row In ResultSet.Tables(0).Rows
                Dim NewNode As TreeNode = New _
                    TreeNode(row("ProductName").ToString())
                NewNode.PopulateOnDemand = False
                NewNode.SelectAction = TreeNodeSelectAction.None
                node.ChildNodes.Add(NewNode)
            Next
        End If
    End Sub
    

    void PopulateProducts(TreeNode node)
    {
        SqlCommand sqlQuery = new SqlCommand();
        sqlQuery.CommandText = "Select ProductName From Products " +
            " Where CategoryID = @categoryid";
        sqlQuery.Parameters.Add("@categoryid", SqlDbType.Int).Value =
            node.Value;
        DataSet ResultSet = RunQuery(sqlQuery);
        if (ResultSet.Tables.Count > 0)
        {
            foreach (DataRow row in ResultSet.Tables[0].Rows)
            {
                TreeNode NewNode = new
                    TreeNode(row["ProductName"].ToString());
                NewNode.PopulateOnDemand = false;
                NewNode.SelectAction = TreeNodeSelectAction.None;
                node.ChildNodes.Add(NewNode);
            }
        }
    }
    

    Этот код аналогичен коду, используемому для заполнения узла категорий. Разница в том, что объект SqlCommand настраивается с параметром, значение которого, равное значению узла, задается во время выполнения, который выбрал пользователь; в данном случае это выбранная категория. Другое различие состоит в том, что свойству PopulateOnDemand присваивается значение false. Это приводит к тому, что узлы продуктов отображаются без кнопки развертывания, так как после продуктов узлов больше нет.

Последний шаг — создание метода, выполняющего запрос и возвращающего набор данных.

Выполнение запроса

  • Добавьте следующую подпрограмму на страницу:

    Function RunQuery(ByVal sqlQuery As SqlCommand) As DataSet
        Dim connectionString As String
        connectionString = _
            ConfigurationManager.ConnectionStrings _
            ("NorthwindConnectionString").ConnectionString
        Dim dbConnection As New SqlConnection
        dbConnection.ConnectionString = connectionString
        Dim dbAdapter As New SqlDataAdapter
        dbAdapter.SelectCommand = sqlQuery
        sqlQuery.Connection = dbConnection
        Dim resultsDataSet As DataSet = New DataSet
        Try
            dbAdapter.Fill(resultsDataSet)
        Catch ex As Exception
            labelStatus.Text = "Unable to connect to SQL Server."
        End Try
        Return resultsDataSet
    End Function
    

    private DataSet RunQuery(SqlCommand sqlQuery)
    {
        string connectionString =
            ConfigurationManager.ConnectionStrings
            ["NorthwindConnectionString"].ConnectionString;
        SqlConnection DBConnection =
            new SqlConnection(connectionString);
        SqlDataAdapter dbAdapter = new SqlDataAdapter();
        dbAdapter.SelectCommand = sqlQuery;
        sqlQuery.Connection = DBConnection;
        DataSet resultsDataSet = new DataSet();
        try
        {
            dbAdapter.Fill(resultsDataSet);
        }
        catch
        {
            labelStatus.Text = "Unable to connect to SQL Server.";
        }
        return resultsDataSet;
    }
    

    В коде создается адаптер обработки данных, основанный на объекте SqlCommand, который ему передается. Затем в коде создается и заполняется набор данных при помощи адаптера.

Теперь можно проверить страницу.

Тестирование страницы

  1. Нажмите CTRL+F5 для запуска страницы.

    Элемент управления TreeView отображается со списком категорий и продуктов.

  2. Щелкните категорию, чтобы убедиться, что она сворачивается и разворачивается, показывая список продуктов каждой категории.

В этом руководстве данных для заполнения элемента управления TreeView использовались иерархические данные XML и данные реляционной базы. Элемент управления TreeView можно использовать для работы со структурой переходов веб-узла и данными XML в качестве табличных (списковых) данных.

Показ: