5. Общее представление об интерфейсах привязки данных

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

я большой сторонник использования в

Создание коллекций и объектов, поддерживающих весь спектр привязки данных, требует массы работы. Я большой сторонник использования в качестве контейнеров для рабочих данных типизированных наборов данных, а не специально определенных объектов, когда их предполагается применять в сценариях привязки данных. Одним из главных доводов в их пользу является то, что набор данных и содержащиеся в нем объекты уже все делают за вас, хорошо проверенным и апробированным образом. В частности, классы Dataview и Data — Rowview предусматривают полную реализацию всех рассмотренных интерфейсов, они будут отлично работать почти с любыми видами данных, которые вам потребуется в них поместить. Если вы передаете данные на уровень представления для привязки данных, вашим первым побуждением должно быть применение для них в качестве контейнера набора данных вместо того, чтобы в интересах объектно-ориентированной чистоты проделывать всю массу работы по корректной реализации объектов и коллекций, которая обеспечит всего лишь их пригодность для привязки данных. Вот некоторые ключевые выдержки из этой главы: Класс DataSet И содержащиеся в нем объекты уже делают за вас все необходимое, поэтому везде, где это возможно, используйте типизированные наборы данных, чтобы не создавать заново все те контейнерные функции, которые уже за вас написаны. Для сильно типизированных классов коллекций, поддерживающих привязку данных, предпочтительнее использовать BindingList<T>. Создавайте классы, производные от BindingList<T>, Чтобы добавить поддержку для сортировки, поиска и фильтрации. Добавьте реализацию INotifyPropertyChanged, Чтобы поддерживать уведомления ListChanged От коллекции BindingList<T>, Когда изменяются значения свойств. Следующая глава заканчивает рассмотрение концепций, стоящих за созданием привязанных к данным приложений Windows Forms, обсуждением верификации и обработки ошибок — двух ключевых моментов построения развитых и надежных приложений, работающих с данными, которые делают именно то, что ожидает от них пользователь. В ней обсуждаются встроенные механизмы верификации и обработки ошибок в элементах управления Windows Forms, а также то, как дополнить имеющиеся функции, чтобы не писать всякий раз один и тот же код верификации и обработки ошибок

Определение специальных типов ячеек и столбцов

однако всегда встречаются особые сценарии

Имея DataGridView, Вы обладаете возможностями представления сложных данных, далеко опережающими возможности DataGrid Благодаря встроенным типам столбцов, которые поддерживаются уже в готовом виде. Однако всегда встречаются особые сценарии, в которых вам понадобится поддерживать отображение столбцов специального вида. К счастью, другим важНыМ преимуществом DataGridView Является простота подключения специальных типов столбцов и ячеек. Если вы хотите настроить только процесс рисования ячейки, но не собираетесь вводить каких-либо новых свойств или средств управления на уровне столбца, у вас есть возможность воспользоваться событиями, а не создавать для этого новые типы столбцов и ячеек. Вы можете обрабатывать событие CellPainting И рисовать прямо в ячейке, при этом можно осуществить многое из того, что вам потребуется, при помощи встроенных типов ячеек и некоторого кода рисования. Но если вы хотите подключать к сетке свои собственные утилизируемые типы столбцов или ячеек с той же легкостью, как используются встроенные типы, то можете создать свои собственные производные классы столбцов и ячеек. Модель, которой вы следуете при подключении специальных типов столбцов, совпадает с той, что вы уже видели при использовании встроенных типов: вам нужно создать тип столбца и соответствующий тип ячеек, которые будут содержаться в столбце. Это делается путем наследования от базовых классов DataGridViewColumn И DataGridViewCell, Непосредственно или косвенно, через один из встроенных классов. Лучше всего объяснить это в подробностях на примере. Допустим, я хочу реализовать специальный тип столбца, позволяющий отображать состояние элементов, представляемых строками сетки. Мне хотелось бы устанавливать состояние, используя перечислимые значения, а ячейка будет графически индицировать состояние в зависимости от установленного для ячейки перечислимого значения. Для этого я определяю классы statusCo-Lumn И StatusCell .

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

метод b main b как

Показан класс приложения для этого примера. Метод Main, Как и раньше, создает экземпляр вашего производного класса приложения и приводит его в действие. При запуске приложения вызывается замещающий метод OnStartingUp, Который позволяет вам создать главное окно и разместить в нем элементы управления. В этом примере я в качестве контейнера верхнего уровня воспользовался элементом управления StackPanel, Чтобы расположить элементы управления вертикально, один над другим. Одним из его дочерних элементов является сетка, которая содержит элементы управления TextBlock И TextField, Отображающие привязанные поля строки. Основная часть кода выполняет элементарные операции WinFx для создания и расположения элементов управления, и аналогична коду на листинге Б.1. Строки кода, относящиеся к привязке данных, выделены жирным шрифтом. Win.DataContext = Custs;Вызовы метода SetBinding Для поля списка и текстовых полей задают путь в контексте данных для этих элементов управления. В случае поля списка свойством, определяющим привязку, является ItemSource, А привязывается оно к экземпляру класса Binding, Создаваемому по умолчанию. Метод SetBinding Принимает аргумент типа DependencyProperty, Предоставляющий информацию о типе свойства в привязанном объекте, которое подлежит привязке, и путь внутри контекста данных. Этот путь будет использоваться во время выполнения для динамического разрешения привязки в соответствии с текущим контекстом данных и информацией о пути, предоставляемой экземпляром объекта Binding. Когда вы создаете экземпляр объекта Binding По умолчанию, в качестве пути устанавливается корень контекста данных. Альтернативно можно задать, как для текстовых полей, путь к подобъекту или коллекции. Для текстовых полей идентифицируется имя свойства в объектах коллекции, которое используется для заполнения свойства Text В TextBox. Данными, с которыми работает этот пример, является специальная коллекция объектов Customer, Создаваемая в обработчике события Window — Loaded И задаваемая в качестве контекста данных для окна через его свойство DataContext. Конструктор по умолчанию класса CustomersCollection Помещает в коллекцию три тестовых объекта, которые мы и видим во время выполнения. После установки контекста данных обновляются привязки всех дочерних элементов управления, и отыскиваются их пути внутри этого контекста.

Обобщенные классы коллекций. NET Framework

net вы реализовывали специальные классы

В. NET 1.1 вы реализовывали специальные классы коллекций, используя класс CollectionBase И лежащий под ним ArrayList. Тут имелись некоторые проблемы, поскольку за кулисами все сохранялось и извлекалось через сырую ссылку Object, Что порождало проблемы с эффективностью, обусловленные упаковкой и распаковкой для типов-значений и приведениями для любых типов. Одним из важнейших нововведений в. NET 2.0 на уровне Framework явились обобщения. Вы уже познакомились с применением обобщений в ряде примеров этой книги, но полное обсуждение обобщений выходит за рамки ее тематики. Тем не менее использование обобщенных классов коллекций является центральным моментом привязки данных в приложениях Windows Forms со специальными рабочими объектами, поскольку обобщенные коллекции решают все проблемы, о которых уже говорилось в этой главе. Когда вы используете обобщенные классы коллекций, вы фактически объявляете сильно типизированный класс коллекции, просто объявляя экземпляр обобщенного класса с параметризованным типом. Рассмотрим, например, следующую строчку кода: Эта строка объявляет элемент-переменную типа List<Customer> И создает экземпляр этого типа. Параметром обобщенного типа является Customer, Который указывает, что должен быть создан новый обобщенный тип List, Содержащий объекты Customer. По синтаксису и семантике обобщения аналогичны шаблонам C++, но реализация их сильно отличается и более эффективна. Это простое объявление эквивалентно по своей функции определению целого класса, подобного показанному в листинге 9.1, но гораздо эффективнее в плане памяти и исполнения. Оно дает вам класс безопасной по типу коллекции для объектов любого рода, просто объявляя новый экземпляр обобщенного типа List<T> С соответствующим параметром типа , Специфицирующим тип объектов, для хранения которых предназначается коллекция.

Элемент управления DetailsView

форматирование элемента управления b detailsview

DetailsView — это новый удобный элемент управления, который устанавливает таблицу, отображающую детали отдельной единицы данных для более естественного просмотра. Форматирование элемента управления DetailsView Можно представить себе так, как будто он поворачивает одиночную строку табличной сетки набок, представляя заголовки столбцов как заголовки строк, а значения полей из желаемой строки как примыкающие к ним ячейки в каждой из этих строк. Пример показан на рис. А. З. Для использования DetailsView Вы устанавливаете управляющий элемент источника данных, как описывалось выше, и помещаете его ID В свойство DataSourcelD Элемента управления DetailsView. Задать, какую следует выбрать строку в источнике данных, вы можете либо ограничив запрос к источнику, чтобы он возвращал только одну единицу данных , Либо установив свойство FilterExpression Значением, которое отфильтрует желаемую строку. Код для страницы, показанной на рис. А. З приведен в листинге А.8.Av

Обратите внимание, что здесь два элемента управления SqlDataSource. Первый установлен как источник данных сетки и получает из базы данных все записи заказчиков. Второй установлен в качестве источника данных для элемента управления DetailsView И посредством ограничения Select . . . Where Определяет, какая строка выбирается. Параметр выбора определяется динамически через ControlParameter, Указывающий на элемент управления сетки, а его свойство SelectedValue Принимает значение ключевого поля выбранной строки, которое содержит CustomeriD. Элемент управления DetailsView Поддерживает также пагинацию, редактирование и многие из других возможностей самого GridView. Он предназначен для операций над единственной строкой за раз, поэтому источник данных должен быть установлен соответствующим образом.