Поделиться через


Разработка пользовательских серверных веб-элементов управления с привязкой к данным для ASP.NET 2.0

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

Серверные веб-элементы управления ASP.NET с привязкой к данным предоставляют пользовательский интерфейс (UI) для источника данных, представляющий коллекцию записей или элементов. Серверные элементы управления Общие сведения о серверном веб-элементе управления GridView, Общие сведения о серверном веб-элементе управления DataList и Общие сведения о серверном веб-элементе управления Repeater являются примерами веб-серверных элементов управления с привязкой к данным. Дополнительные сведения о серверных веб-элементах управления с привязкой к данным в составе ASP.NET см. в разделе Общие сведения о серверных веб-элементах управления ASP.NET с привязкой к данным.

В ASP.NET версии 2.0 новая модель источников данных позволяет привязывать элементы управления с привязкой к данным к элементам-источникам, позволяя вынести общие операции с данными — например, разбиение по страницам, сортировку и удаление — из самого элемента управления с привязкой к данным. Эта модель обеспечивает большую степень гибкости элементов управления с привязкой к данным при разработке веб-страниц и повышает уровень повторного использования.

В этом разделе описываются основные шаги, необходимые для реализации пользовательских серверных веб-элементов управления ASP.NET 2.0. Дополнительные сведения об общей архитектуре и реализации пользовательских элементов управления см. в разделах Разработка пользовательских серверных элементов управления ASP.NET и Пошаговое руководство. Создание и использование пользовательского серверного элемента управления. Дополнительные сведения о разработке элементов управления с привязкой к данным, совместимых с платформой ASP.NET 1.1, см. в разделах Разработка пользовательских серверных веб-элементов управления с привязкой к данным для ASP.NET 1.1 и Пошаговое руководство. Создание пользовательского веб-элемента привязки данных ASP.NET для ASP.NET 1.1. Дополнительные сведения об элементах управления источников данных см. в разделе Общие сведения об элементах управления источниками данных.

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

Перед созданием собственного пользовательского элемента управления с привязкой к данным изучите возможности существующих элементов управления с привязкой к данным, представленных в ASP.NET. Может оказаться так, что существующие элементы управления полностью удовлетворяют требования разработчика, или же можно ограничиться созданием пользовательского элемента управления, который расширяет существующий элемент управления, представляющий большинство требуемых возможностей. Дополнительные сведения о серверных веб-элементах управления с привязкой к данным в составе ASP.NET см. в разделе Общие сведения о серверных веб-элементах управления ASP.NET с привязкой к данным.

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

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

  • Требуется создать пользовательский элемент управления с привязкой к данным, который предварительно компилируется и распространяется отдельно от программы.

  • Требуется расширить возможности имеющегося в ASP.NET элемента управления с привязкой к данным.

  • Требуется создать элемент управления с привязкой к данным со специализированным визуальным конструктором, который соответствует определенным требованиям.

Основные функциональные возможности пользовательского элемента управления с привязкой к данным

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

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

  • Поддержку источников данных для универсальных интерфейсов IEnumerable и IListSource.

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

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

Использование доступных функций времени конструирования

Существуют функции времени конструирования, доступные всем серверным веб-элементам управления, которые могут потребоваться для пользовательского элемента управления с привязкой к данным. Для пользовательского элемента управления можно создать визуальный конструктор класса и шаблоны элементов управления. Эти функции применяются при использовании элемента управления во время конструирования в рабочей области конструирования, например, в режиме конструктора в Visual Studio.

Создание визуального конструктора элемента управления может значительно повысить удобство работы с пользовательским элементом управления во время конструирования, поскольку при этом предоставляется интерфейс времени конструирования, позволяющий разработчикам настраивать свойства элемента управления. Общие сведения о конструкторах элементов управления ASP.NET см. в разделе Общие сведения о конструкторах элементов управления ASP.NET. Примеры см. в разделах HierarchicalDataBoundControlDesigner и Пошаговое руководство. Создание базового конструктора элементов управления для серверного веб-элемента управления.

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

Реализация пользовательского элемента управления c привязкой к данным в ASP.NET 2.0

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

Шаг

Сводка шага

Выбор базового класса элемента управления с привязкой к данным.

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

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

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

Запуск извлечения данных.

  • Извлеките данные, присвоенные разработчиком страницы элементу управления, выполнив следующие действия:

  • Переопределите метод PerformSelect базового класса элемента управления с привязкой к данным.

  • Вызовите метод GetData базового класса элемента управления с привязкой к данным для извлечения представления источника данных элемента управления.

  • Вызовите метод Select объекта DataSourceView для запуска извлечения данных и укажите метод обратного вызова, который получит данные.

Обработка извлеченных данных.

Предоставьте метод обратного вызова, указанный в качестве параметра в методе Select. Метод обратного вызова должен иметь единственный параметр типа IEnumerable для получения данных. Если для элемента управления требуется обработка данных, то она должна происходить внутри этого метода обратного вызова.

Создание объектов пользовательского интерфейса, представляющих данные.

Переопределите метод PerformDataBinding. В этом методе необходимо выполнить следующие задачи:

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

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

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

Разработчики элементов управления могут расширить один из доступных базовых классов элементов управления с привязкой к данным, чтобы создать пользовательский элемент управления с привязкой к данным. В следующей таблице предоставлен список базовых классов привязки данных, доступных в ASP.NET 2.0. Просмотрите описания каждого класса и определите, какой базовый класс лучше всего подходит под требования пользовательского элемента управления с привязкой к данным. Дополнительные сведения о каждом базовом классе элементов управления с привязкой к данным, а также примеры реализации см. в справочной документации для каждого класса. Дополнительные сведения о серверных веб-элементах управления с привязкой к данным в составе ASP.NET см. в разделе Общие сведения о серверных веб-элементах управления ASP.NET с привязкой к данным.

Класс

Описание

BaseDataBoundControl

  • Это базовый класс всех элементов управления с привязкой к данным, выполняющий привязку данных и проверку всех связанных данных.

DataBoundControl

Это базовый класс привязки данных для создания стандартных элементов управления с привязкой к данным. DataBoundControl отвечает за следующее:

  • Предоставляет базовую реализацию, совместно используемую всеми элементами управления с привязкой к данным.

  • Содержит логику для обмена информацией с элементами управления источников данных и контейнерами данных.

  • Служит основой для элементов управления с привязкой к данным, например, TreeView и ListControl.

ListControl

  • Это базовый класс для элементов управления «Список», который расширяет класс DataBoundControl. Он предоставляет коллекцию Items и дополнительные возможности отрисовки макета.

CompositeDataBoundControl

  • Это базовый класс, который расширяет класс DataBoundControl, предоставляя следующие функциональные возможности:

  • Реализует обычный код, требуемый сложными элементами управления, в том числе код, восстанавливающий иерархию дочерних элементов управления элемента управления по состоянию просмотра после выполнения обратной передачи.

  • Осуществляет привязку к источнику данных IEnumerable и перечисляет данные, формируя дерево элементов управления.

  • Служит основой для элементов управления с привязкой к данным, например, GridView и DetailsView.

HierarchicalDataBoundControl

  • Это базовый класс для элементов управления, в которых данные отображаются в иерархической форме. Он служит основой для иерархических элементов управления с привязкой к данным, например, TreeView и Menu.

Предоставленные свойства привязки данных

В базовых классах элементов управления с привязкой к данным уже предоставляется ряд свойств привязки данных, необходимых для того, чтобы разработчик веб-страниц мог привязать источник данных к элементу управления. Дополнительных действий со стороны разработчика элемента управления не требуется. Наследование от DataBoundControl, например, позволяет пользовательскому элементу управления получить три предоставляемых свойства привязки данных:DataSourceID, DataSource и DataMember. Затем разработчик страницы может указать источник данных, к которому элемент управления осуществит привязку путем задания значения свойства DataSource или DataSourceID.

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

Свойство DataSource позволит разработчику страницу осуществить привязку элемента управления с привязкой к данным непосредственно к объектам данных следующих двух типов:

  • К объекту, реализующему интерфейс IEnumerable, (например, объекту Array, ArrayList или Hashtable).

  • К объекту, реализующему интерфейс IListSource (например, объекту DataSet).

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

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

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

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

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

Inherits DataBoundControl

Public Property DataTextField() As String
    Get
        Dim o As Object = ViewState("DataTextField")
        If o Is Nothing Then
            Return String.Empty
        Else
            Return CStr(o)
        End If
    End Get
    Set(ByVal value As String)
        ViewState("DataTextField") = value
        If (Initialized) Then
            OnDataPropertyChanged()
        End If
    End Set
End Property
public class SimpleDataBoundColumn : DataBoundControl
{
    public string DataTextField
    {
        get
        {
            object o = ViewState["DataTextField"];
            return ((o == null) ? string.Empty : (string)o);
        }
        set
        {
            ViewState["DataTextField"] = value;
            if (Initialized)
            {
                OnDataPropertyChanged();
            }
        }
    }

Запуск извлечения данных

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

Для извлечения данных выполните в переопределенном методе PerformSelect следующие задачи:

  1. Определите, использовалось ли разработчиком страницы свойство DataSource или свойство DataSourceID для задания данных, подлежащих привязке к элементу управления. Это можно сделать путем проверки свойства IsBoundUsingDataSourceID. Например, значение false свойства IsBoundUsingDataSourceID указывает на то, что свойство DataSource использовалось для указания источника данных.

  2. Если разработчик страниц задал свойство DataSource, то требуется дополнительный шаг: вызовите метод OnDataBinding.

  3. Вызовите метод GetData для извлечения объекта DataSourceView, связанного с элементом управления с привязкой к данным.

  4. Вызовите метод Select извлеченного объекта DataSourceView для запуска извлечения данных и для указания метода обратного вызова, который будет обрабатывать извлеченные данные. Метод Select работает асинхронно, поэтому во время извлечения данных может вестись другая деятельность.

  5. Укажите завершение задач PerformSelect путем задания значения false для свойства RequiresDataBinding и последующего вызова метода MarkAsDataBound.

  6. Создайте событие OnDataBound.

В следующем примере кода демонстрируется выполнение описанных выше задач извлечения данных в переопределенной версии метода PerformSelect.

Protected Overrides Sub PerformSelect()
    ' Call OnDataBinding here if bound to a data source using the
    ' DataSource property (instead of a DataSourceID), because the
    ' databinding statement is evaluated before the call to GetData.       
    If Not IsBoundUsingDataSourceID Then
        OnDataBinding(EventArgs.Empty)
    End If

    ' The GetData method retrieves the DataSourceView object from  
    ' the IDataSource associated with the data-bound control.            
    GetData().Select(CreateDataSourceSelectArguments(), _
        AddressOf OnDataSourceViewSelectCallback)

    ' The PerformDataBinding method has completed.
    RequiresDataBinding = False
    MarkAsDataBound()

    ' Raise the DataBound event.
    OnDataBound(EventArgs.Empty)

End Sub
protected override void PerformSelect()
{
    // Call OnDataBinding here if bound to a data source using the
    // DataSource property (instead of a DataSourceID), because the
    // databinding statement is evaluated before the call to GetData.       
    if (!IsBoundUsingDataSourceID)
    {
        this.OnDataBinding(EventArgs.Empty);
    }

    // The GetData method retrieves the DataSourceView object from  
    // the IDataSource associated with the data-bound control.            
    GetData().Select(CreateDataSourceSelectArguments(),
        this.OnDataSourceViewSelectCallback);

    // The PerformDataBinding method has completed.
    RequiresDataBinding = false;
    MarkAsDataBound();

    // Raise the DataBound event.
    OnDataBound(EventArgs.Empty);
}

Обработка извлеченных данных

Создайте собственный метод обратного вызова, чтобы принять извлеченные данные. Это метод обратного вызова, указанный при вызове метода Select в переопределенной версии метода PerformSelect. Метод обратного вызова должен содержать единственный параметр типа IEnumerable. В методе обратного вызова можно выполнить любую обработку возвращенных данных, если это необходимо элементу управления. В качестве последнего шага вызовите метод PerformDataBinding.

В следующем примере кода демонстрируется метод обратного вызова, который имеет параметр типа IEnumerable и вызывает метод PerformDataBinding.

Private Sub OnDataSourceViewSelectCallback(ByVal retrievedData As IEnumerable)
    ' Call OnDataBinding only if it has not already been 
    ' called in the PerformSelect method.
    If IsBoundUsingDataSourceID Then
        OnDataBinding(EventArgs.Empty)
    End If
    ' The PerformDataBinding method binds the data in the  
    ' retrievedData collection to elements of the data-bound control.
    PerformDataBinding(retrievedData)

End Sub
private void OnDataSourceViewSelectCallback(IEnumerable retrievedData)
{
    // Call OnDataBinding only if it has not already been 
    // called in the PerformSelect method.
    if (IsBoundUsingDataSourceID)
    {
        OnDataBinding(EventArgs.Empty);
    }
    // The PerformDataBinding method binds the data in the  
    // retrievedData collection to elements of the data-bound control.
    PerformDataBinding(retrievedData);
}

Создание объектов пользовательского интерфейса, представляющих данные

В переопределенной версии метода PerformDataBinding можно создать дочерние элементы управления, которые будут представлять данные. При этом перебираются элементы коллекции данных и создаются дочерние элементы управления, а их свойства задаются на основе каждого элемента данных. Добавление новых дочерних элементов управления в коллекцию Controls элемента управления позволяет их отрисовывать. Иерархия элементов управления отрисовывается во время выполнения наследуемого метода Render элемента управления. Можно переопределить метод Render для выполнения специальной отрисовки, требуемой пользовательским элементом управления, например, включения дополнительных элементов HTML или специальной отрисовки для отображения в режиме конструирования.

Для создания объектов пользовательского интерфейса, представляющих данных, переопределите метод PerformDataBinding и выполните следующие задачи:

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

  2. Переберите элементы коллекции данных и создайте дочерние элементы управления, которые будут представлять данные в отображении пользовательского интерфейса. Добавьте все дочерние элементы управления в коллекцию элемента управления путем вызова метода Add элемента управления.

  • В следующем примере кода показано переопределение метода PerformDataBinding. Метод PerformDataBinding вызывается, чтобы обеспечить возможность выполнения любого другого кода, полагающегося на этот метод. При этом перебираются элементы коллекции данных и создаются дочерние элементы управления, представляющие данные в отображении пользовательского интерфейса.
        Protected Overrides Sub PerformDataBinding(ByVal retrievedData As IEnumerable)
            MyBase.PerformDataBinding(retrievedData)

            ' Verify data exists.
            If Not (retrievedData Is Nothing) Then
                Dim tbl As New Table()
                Dim row As TableRow
                Dim cell As TableCell
                Dim dataStr As String = String.Empty

                Dim dataItem As Object
                For Each dataItem In retrievedData
                    ' If the DataTextField was specified get the data
                    ' from that field, otherwise get the data from the first field. 
                    If DataTextField.Length > 0 Then
                        dataStr = DataBinder.GetPropertyValue(dataItem, DataTextField, Nothing)
                    Else
                        Dim props As PropertyDescriptorCollection = TypeDescriptor.GetProperties(dataItem)
                        If props.Count >= 1 Then
                            If Nothing <> props(0).GetValue(dataItem) Then
                                dataStr = props(0).GetValue(dataItem).ToString()
                            End If
                        End If
                    End If

                    row = New TableRow()
                    tbl.Rows.Add(row)
                    cell = New TableCell()
                    cell.Text = dataStr
                    row.Cells.Add(cell)
                Next dataItem

                Controls.Add(tbl)
            End If

        End Sub
    End Class
End Namespace
protected override void PerformDataBinding(IEnumerable retrievedData)
{
    base.PerformDataBinding(retrievedData);

    // Verify data exists.
    if (retrievedData != null)
    {
        Table tbl = new Table();
        TableRow row;
        TableCell cell;
        string dataStr = String.Empty;

        foreach (object dataItem in retrievedData)
        {
            // If the DataTextField was specified get the data
            // from that field, otherwise get the data from the first field. 
            if (DataTextField.Length > 0)
            {
                dataStr = DataBinder.GetPropertyValue(dataItem,
                    DataTextField, null);
            }
            else
            {
                PropertyDescriptorCollection props =
                        TypeDescriptor.GetProperties(dataItem);
                if (props.Count >= 1)
                {
                    if (null != props[0].GetValue(dataItem))
                    {
                        dataStr = props[0].GetValue(dataItem).ToString();
                    }
                }
            }

            row = new TableRow();
            tbl.Rows.Add(row);
            cell = new TableCell();
            cell.Text = dataStr;
            row.Cells.Add(cell);
        }

        this.Controls.Add(tbl); 
    }
}

Построение пользовательского серверного элемента управления

Дополнительные сведения о построении пользовательских серверных веб-элементов управления с привязкой к данным и их использовании на веб-странице см. в разделе Примеры связывания пользовательского серверного элемента управления.

См. также

Задачи

Пошаговое руководство. Создание пользовательского веб-элемента привязки данных ASP.NET для ASP.NET 2.0

Пошаговое руководство. Создание и использование пользовательского серверного элемента управления

Основные понятия

Общие сведения о серверных веб-элементах управления ASP.NET с привязкой к данным

Атрибуты метаданных для специализированных серверных элементов управления

Общие сведения о конструкторах элементов управления ASP.NET

Ссылки

HierarchicalDataBoundControlDesigner

Другие ресурсы

Разработка пользовательских серверных элементов управления ASP.NET