WWW.DISSERS.RU

БЕСПЛАТНАЯ ЭЛЕКТРОННАЯ БИБЛИОТЕКА

   Добро пожаловать!

Pages:     | 1 |   ...   | 8 | 9 ||

«Петр Дарахвелидзе Евгений Марков Санкт-Петербург «БХВ-Петербург» 2003 УДК 681.3.06 ББК 32.973.26-018.2 Д20 П. Г., Марков Е. П. ...»

-- [ Страница 10 ] --

Для создания наборов данных, которые можно представить в виде кросста ба, используются запросы SQL с применением группирующего оператора GROUP BY и агрегатных функций. Если обратиться к топологическим анало гиям, то набор данных такого запроса представляет собой многомерный гиперкуб, каждая сторона которого соответствует одному полю набора данных.

Для дальнейшего изложения необходимо ввести еще одно понятие. Сово купность строк или колонок, имеющих отношение к одному полю набора данных, будем называть размерностью. Размерность представляет собой вир туальную плоскость, которая рассекает многомерный куб данных парал лельно какой-либо стороне этого куба. Компоненты многомерного пред ставления данных как раз предназначены для того, чтобы визуализировать это n-мерное сечение.

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

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

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

О перед отображением данных необходимо настроить параметры размерно стей кросстаба;

• непосредственный показ данных в кросстабе;

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

734 Часть VII. Технологии программирования Для этого в форме приложения требуется разместить как минимум пять компонентов со страницы Decision Cube Палитры компонентов.

Для создания запроса SQL можно использовать компонент TDecisionQuery ИЛИ обычный TQuery.

Запрос должен быть связан с компонентом TDecisionCube, который осуще ствляет подготовку набора данных запроса к многомерному показу.

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

Непосредственный показ многомерного набора данных проводится при по мощи КОМПОНеНТОВ И TDecisionGraph. ДОЛЖНЫ вать соединение С компонентом TDecisionSource.

Наконец, управление многомерным представлением данных реализует ком понент TDecisionPivot, он также должен быть связан с компонентом TDecisionSource.

Допустим, что на форме расположены следующие компоненты:

TDecisionQuery ПО имени TDecisionCube ПО TDecisionSource ПО имени TDecisionGrid ПО • TDecisionPivot ПО имени DecisionPivotl.

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

Таблица Как связать компоненты многомерного представления данных Свойство Значение Описание DataSet j DecisionQueryl ] Определяет компонент доступа к данным, I | который создает набор данных DecisionCubel | Указывает на компонент формирования DecisionCube многомерного набора данных TDecisionGrid DecisionSource DecisionSourcel I Ссылается на компонент TDecisionSource Глава 30. Многомерное представление данных Таблица (окончание) Значение Описание TOecisionPivot DecisionSource DecisionSourcel Ссылается на компонент TDecisionSource Если задать текст запроса SQL и открыть набор данных, то вся цепочка за работает, причем ее поведение ничем не отличается от поведения во время выполнения приложения.

Теперь, когда мы узнали, как объединить компоненты многомерного пред ставления данных в единую систему, настало время более подробно изучить возможности каждого компонента.

Подготовка набора данных Компоненты многомерного представления данных работают со специально созданным и подготовленным набором данных. Эта работа выполняется специальным компонентом доступа к данным — TDecisionQuery. Его непо средственным предком является компонент TQuery.

Набор данных формируется при помощи запроса, который основан на стандартном синтаксисе SQL 92. Для обеспечения работы многомерного представления данных запрос должен удовлетворять ряду требований.

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

2. Поля запроса должны быть сгруппированы при помощи оператора GROUP BY.

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

Компонент TDecisionQuery должен только обеспечить выполнение запроса и создание набора данных, он не имеет никаких дополнительных свойств или методов. Поэтому для создания набора данных можно использовать и обыЧНЫЙ TQuery. Преимущество TDecisionQuery СО СТОИТ в том, что он имеет специализированный редактор для создания тек ста запроса (рис. 30.2). Он вызывается командой Decision Query Editor из всплывающего меню компонента или двойным щелчком на компоненте.

Элементы управления страницы Dimensions/Summaries позволяют создавать текст запроса, манипулируя именами полей таблиц. Псевдоним базы дан ных выбирается в комбинированном списке Database. После этого в списке Table задается нужная таблица. Если в запросе требуется использовать не 736 Часть VII. Технологии программирования сколько таблиц, то для их выбора можно воспользоваться утилитой SQL Builder, которая вызывается щелчком на одноименной кнопке.

(Decision Query Editor SQL Query J Fields:

REP STATUS S.ORDER DATE S.SHI P DATE NEEDED S.PAI D S.QTY ORDERED S.TOTAL VALUE TYPE Averages Cancel;

30.2. Специализированный редактор компонента TDeci si onQuery Из списка доступных полей при помощи кнопок Add требуемые поля мож но перенести в список полей — размерностей Dimensions и список сумми рующих полей Поля из этих списков используются при созда нии запроса.

Запрос формируется автоматически при работе с описанными элементами управления. Текст запроса доступен для просмотра и редактирования на странице SQL Query.

Подготовка набора данных к многомерному представлению осуществляется компонентом TDecisionCube. Его основная задача — создание размерностей для многомерной структуры данных на основе каждого поля набора данных.

Для каждой размерности в компоненте можно задать ряд параметров, кото рые определяют ее поведение и внешний вид.

Компонент TDecisionCube формирует размерности при открытии набора данных, причем созданное многомерное представление данных полностью работоспособно уже во время разработки. Для этого достаточно присвоить СВОЙСТВУ Active компонентов TDecisionQuery ИЛИ TQuery True. По сле этого любой визуальный компонент многомерного представления начи нает работать так же, как и во время выполнения.

Компонент TDecisionCube также позволяет управлять использованием памя ти многомерного представления данных. Дело в том, что при добавлении к многомерному представлению новой размерности объем занимаемой па мяти возрастает в арифметической профессии. Поэтому возможность огра Глава 30. Многомерное представление данных ничения размеров используемой памяти особенно актуальна для больших наборов данных.

Все основные настройки компонента выполняются при помощи специали зированного редактора свойства (рис. 30.3).

Available fields Цате (Заказчик Type Needed Type |None firouping Cancel 30.3. Специализированный редактор свойства DecisionMap компонента TDecisionCube (страница Dimension Settings) Для настроек размерностей используется страница Dimension Settings этого редактора. В расположенном слева списке Available Fields содержатся все поля набора данных. В элементах управления справа приведены параметры размерности для выбранного поля.

В однострочном Display Name задается название поля, которое будет присутствовать в визуальных компонентах многомерного просмотра.

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

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

Active — данные поля видны сразу после открытия формы и набора данных во время выполнения или сразу после открытия набора данных во время разработки;

As Needed — данные поля становятся видны после выполнения пользова телем во время выполнения или разработчиком во время разработки дей ствий по отображению данных;

inactive — данные поля не видны.

738 Часть VII. Технологии программирования Однострочный редактор Format содержит строку форматирования для дан ных Комбинированный список Grouping необходим для того, чтобы определить, какие значения будут показаны. Варианты Year, Quarter, Month возможны только для полей с календарным типом данных.

Однострочный редактор Initial Value задает начальное значение для поля.

Страница Memory Control используется для управления расходом памяти для нужд компонента (рис. 30.4). Однострочные редакторы Dimensions, Summaries и Cells в ряду Maximum позволяют задать максимальное число размерностей, сумм и ячеек, соответственно.

Decision Cube Editor r Data '.

: j'...:

Display Values, ••..| 30.4. Специализированный редактор свойства компонента TDecisionCube (страница Memory Control) Аналогичные значения в ряду Current показывают текущее число этих структур.

Аналогичные значения в ряду Active+Needed показывают общее возможное число размерностей, сумм и ячеек.

Значения в ряду Active показывают число видимых размерностей сумм и ячеек.

Кнопка Get Cell Counts выполняет запрос, который возвращает число ячеек в кросстабе.

Группа радиокнопок Designer Data Options задает режим показа данных во время разработки:

Глава 30. Многомерное представление Display Dimension Names — отображаются только названия размерностей;

Display Names and Values — отображаются названия размерностей и зна чения;

Display Names, Values, and Totals — отображаются названия, значения и суммы размерностей;

О Run Time Display Only — визуализация данных осуществляется только во время выполнения.

Подготовленный к использованию для многомерного отображения набор данных необходимо связать с визуальными компонентами. Это делается при помощи компонента TDecisionSource. Через один такой компонент с набором данных можно связать несколько визуальных компонентов (см. табл. 30.1).

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

Компонент Компонент доступа к данным TDecisionQuery предназначен для создания набора данных, который был бы пригоден для многомерного представле ния. Для создания набора данных используется запрос SQL. Требования к запросу приведены выше.

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

Компонент TDecisionCube Компонент TDecisionCube осуществляет преобразование набора данных, ко торый Содержится В TDecisionQuery, К ВИДУ, ДОСТуПНОМу ДЛЯ отображения визуальными компонентами многомерного представления данных (табл. 30.2). Обычную таблицу набора данных компонент преобразу ет в многомерный кросстаб. Число размерностей создаваемого кросстаба зависит от числа полей данных набора данных. Значения в ячейках кросста ба зависят от типа агрегатной функции в запросе SQL.

Таблица 30.2. Свойства и методы компонента TDecisionCube Объявление | Тип ! Описание Свойства Разрешает или запрещает преобра property Active: Boolean;

j Pu зование набора данных в кросстаб 740 Часть VII. Технологии программирования Таблица 30,2 (продолжение) Объявление | Тип Описание property BinData: Boolean;

Ro Значение True означает, что хотя бы одна размерность находится в свер нутом состоянии (данные не отобра жаются) property Capacity: Integer;

Определяет число байтов, используемых для хранения многомерного массива property Integer;

Содержит индекс текущей суммы кросстаба property DataSet: TDataSet;

Ссылка на экземпляр набора данных, который отображается в кросстабе type Задает режим отображения данных (dsNoData, в кросстабе:

;

• dsNoData — во время разработки property DesignState:

данные не видны;

TCubeDesignState;

• dsMetaData — видны названия размерностей;

• dsDimensionData — видны назва ния размерностей и значения, суммы не видны;

• — видны все данные property Integer;

Ro Возвращает число размерностей property Индексированный список ссылок на объекты параметров размерностей property Общее число полей набора данных, Integer;

включая поля размерностей и сумм Задает максимальное число ячеек property Integer;

кросстаба Задает максимальное число property Integer;

размерностей property Integer;

Задает максимальное число сумм property ShowProgressDialog: При значении True при подготовке Boolean;

кросстаба отображается индикатор property Integer;

Возвращает число активных сумм кросстаба Методы function Pu ] Возвращает текст запроса SQL, [ который может быть использован SelectList:

| для создания набора данных, string;

bActive: Boolean):

| включающего данные из кросстаба string;

I без сумм Глава 30. Многомерное представление данных Таблица 30.2 (окончание) Объявление Тип Описание function GetSQL(ValueArray: Возвращает текст запроса SQL, кото bActive: рый может быть использован для соз Boolean): string;

| дания набора данных, включающего j данные из кросстаба без сумм procedure ShowCubeDialog;

Вызывает специализированный редактор компонента procedure | Обновляет список объектов парамет bForce: Boolean);

| ров размерностей Методы-обработчики событий type TCubeRefreshEvent = Вызывается сразу после закрытия компонента (Active := False) TCubeDims) of object;

property OnRefresh:

TCubeRefreshEvent;

property AfterClose: TCubeNotifyEvent;

property AfterOpen: Вызывается сразу после открытия := False) property BeforeClose: Вызывается перед закрытием : False) property BeforeOpen: Pb Вызывается перед открытием TCubeNotifyEvent;

:= False) TErrorAction = (eaFail, Pb | Вызывается после того, как занимае мый кросстабом объем памяти eaContinue);

превысит заданный предел TCapacityErrorEvent EAction:

TErrorAction) of object;

property TCapacityErrorEvent ;

При помощи методов и можно получить тексты запро сов, которые возвращают набор данных, соответствующий кросстабу с за данным параметрами состояниями. Массив содержит условия для полей размерностей. Первой размерности соответствует первый элемент массива, второй размерности — второй элемент и т. д. Если значение эле мента меньше нуля, то в результат запроса попадают все значения поля размерности. Значение элемента, равное или больше нуля, определяет ин декс значения поля размерности. Параметр содержит разделенный запятыми список дополнительных полей, которые нужно включить в за Часть VII. Технологии программирования Параметр bActive накладывает дополнительное ограничение на раз мерности. При значении True в результат запроса автоматически (без ис пользования параметра selectList) попадают только активные размерности.

Ключевым свойством компонента является свойство которое позволяет установить параметры размерностей и максимальный размер ис пользуемой памяти. Для этих целей применяется специализированный ре дактор (см. рис. 30.4).

Это свойство представляет собой экземпляр класса который ин капсулирует индексированный список экземпляров объектов TCubeDim, каж дый из которых содержит информацию о параметрах одной размерности.

Основные свойства этого класса представлены в табл. 30.3.

Таблица 30.3. Основные свойства класса TCubeDim Объявление Тип Описание type TActiveFlags = (diActive, Определяет режим отображения diAsNeeded, данных размерности property ActiveFlag:

TActiveFlags;

property BaseName: string;

Содержит имя поля размерности в таблице базы данных property string;

Определяет способ форматирования диапазона значений размерности type TBinType = (binNone, Определяет способ группирования binYear, binQuarter, данных в размерности binSet, property BinType: TBinType;

type = Определяет тип размерности dimGenericAgg, property TDimFlags;

property FieldName: String;

Содержит имя поля в наборе данных property FieldType: TFieldType;

Определяет тип поля property Format: String;

Задает форматирование данных размерности property Loaded: Boolean;

Значение True говорит о том, что данный элемент загружен в многомерный набор данных Глава 30. Многомерное представление данных Таблица 30.3 (окончание) Объявление Тип Описание property StartDate: TDate;

Pu Определяет начальный элемент для группировки дате property StartValue: String;

| Определяет начальный элемент для группировки по значению property ValueCount: Integer;

| Возвращает число уникальных элементов в размерности Компонент TDecisionSource Компонент TDecisionSource предназначен для связывания визуальных ком понентов многомерного представления с компонентом TDecisionCube (табл. 30.4). Кроме того, за счет возможности подключения к этому компо ненту нескольких визуальных компонентов одновременно, при изменении состояния одного визуального компонента осуществляется синхронизация многомерного представления во всех остальных компонентах.

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

Таблица 30.4. Основные свойства компонента TDecisionSource Объявление Описание type TDecisionControlType = Определяет способ управления xtRadioEx) отдельной размерностью в компоненте TDecisionGrid property ControlType:

TDecisionControlType;

property Integer;

Содержит индекс текущей суммы в компоненте TDecisionGrid property DecisionCube: Связывает данный компонент TDecisionCube;

С компонентом TDecisionCube.

Содержит ссылку на экземпляр компонента TDecisionCube property Ready: Boolean;

Значение True означает, что данный компонент связан с активным компонен том TDecisionCube property SparseCols: Boolean;

При значении True из компонента TDecisionGrid удаляются пустые Часть VII. Технологии программирования Таблица 30.4 (окончание) Объявление Описание property Boolean;

При значении True из компонента удаляются пустые строки Компонент имеет средства для управления состоянием многомерного пред ставления в визуальных компонентах. Для этого используется свойство Рассмотрим его возможные значения:

xtCheck — ЩеЛЧОК На КНОПКаХ размерности В TDecisionGrid и TDecisionPivot приводит к открытию или закрытию размерности;

xtRadio — щелчок на кнопках размерности в компонентах TDecisionGrid и TDecisionPivot приводит к открытию или закрытию данной размерно сти и закрытию всех остальных в этом направлении;

xtRadioEx — ЩеЛЧОК КНОПКаХ раЗМерНОСТИ В TDecisionGrid и TDecisionPivot приводит к открытию или закрытию данной размер ности и закрытию или открытию всех остальных размерностей в этом направлении.

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

С компонентом они связаны при помощи компонента (см. выше).

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

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

Для управления графиком во время выполнения можно использовать ком понент TDecisionPivot.

Глава 30. Многомерное представление данных В табл. 30.5 приведены основные свойства и методы компонента.

Таблица 30.5. Свойства и методы компонента TDecisionGrid Объявление Тип | Описание Свойства property Ro Индексированный массив значений Integer]: string;

всех ячеек компонента в строковом I формате property ColCount: Integer;

Возвращает общее число колонок Ro в сетке property DecisionSource: РЬ | Указывает на компонент | TDecisionSource, через который | осуществляется связь с набором property Объект представляет индексированный список объектов визуальных свойств размерностей Возвращает число фиксированных property Integer;

Ro колонок, которые используются | отображения информации о размер I ностях (названия, значения, обозна I чения) I Возвращает число фиксированных property Integer;

| строк, которые используются для I отображения информации о размер | ностях (названия, значения, | обозначения) | Определяет общие настройки компо type нента:

TDecisionGridOption = (cgGridLines, I • cgGridLines — отображаются cgPivotable);

| вертикальные и горизонтальные | разделительные линии;

TDecisionGridOptions = set of TDecisionGridOption;

| • cgOutliner — отображаются property Options: | элементы управления в виде TDecisionGridOptions;

знаков "+" и "-" для открытия и закрытия размерностей;

cgPivotable — размерности мож но переупорядочивать при помощи перетаскивания Возвращает общее число строк Ro property Integer;

в сетке Часть VII. Технологии программирования Таблица 30.5 (окончание) Объявление I Тип I Описание property Boolean;

i Pb Разрешает или запрещает использо вание специализированного редакто ра компонента TDeclsionCube property Totals: Boolean;

При значении True сетка имеет промежуточные суммы по каждой колонке и строке Методы type Pu | Позволяет определить назначение | любой ячейки сетки. Параметры ACol = ] j и ARow определяют положение ячейки (dsGroupStart, | в сетке.

dsColCaption, i dsColValue, j [ В параметре возвращается dsData, dsOpenAfter, | строка, содержащая значение в том dsCloseAfter, | виде, как оно представлено в ячейке.

dsOpenBefore, dsRowIndicator, | Параметр DrawState возвращает dsColIndicator, | I информацию о назначении ячейки dsColPlus, dsNone);

= set | of TDecisionDrawStates;

j function | ARow: Integer;

var Value: \ string;

var DrawState: | TDecisionDrawState): boolean;

| function | Pu Возвращает индексы всех полей, дан ARow: Integer;

var ValueArray:

ные которых суммированы в ячейке.

TValueArray): boolean;

Параметр ValueArray содержит индексы полей Компонент TDecisionGrid является предком класса TCustomGrid и поэтому обладает всеми базовыми свойствами и методами, присущими сетке.

Для доступа к значению каждой ячейки используется свойство Адре сация ячеек осуществляется с левой верхней ячейки, которая имеет индексы [0,0].

Свойство Dimensions является экземпляром объекта который инкапсулирует индексированный список указателей на экземпляры объек тов Каждый такой объект содержит важнейшие визуальные свойства размерностей. При щелчке на кнопке в однострочном редакторе свойства в Инспекторе объектов разворачивается список всех таких объ ектов.

Глава 30. Многомерное представление данных Компонент TDecisionGraph Компонент TDecisionGraph создает график на основе многомерного пред ставления набора данных. Конкретный вид графика (назначение горизон тальной и вертикальной осей) зависит от настроек компонентов TDecisionCube и TDecisionPivot. По умолчанию к оси абсцисс привязывается первая вер тикальная размерность, к оси ординат — первая сумма. Первая горизон тальная размерность отображается в легенде графика.

Одним из предков компонента TDecisionGraph является класс TChart, от ко торого унаследованы все многочисленные свойства и методы для настройки графика.

Для подключения к графику набора данных используется свойство property DecisionSource: TDecisionSource;

которое ссылается на экземпляр компонента источника данных.

Сразу после подключения автоматически строится график с осями, задан ными по умолчанию.

Для управления графиком во время выполнения можно использовать ком понент TDecisionPivot.

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

Взаимное положение и расположение размерностей по сторонам кросстаба никак не связано с местом полей в запросе компонента TDecisionQuery.

Все операции по управлению многомерным представлением сосредоточены в одном компоненте — TDecisionPivot (см. 30.2). В некоторой степени это аналог компонента TDBNavigator, только TDecisionPivot управляет не записями набора данных, а размерностями многомерного представления данных.

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

748 Часть VII. Технологии программирования Компонент TDecisionPivot Компонент TDecisionPivot предоставляет пользователю средства управления размерностями многомерного представления данных. В стандартном со стоянии компонент представляет собой панель, разделенную на три части (табл. 30.6). Каждая часть имеет собственный набор кнопок.

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

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

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

Кнопка в нажатом состоянии показывает размерность. Одновременно ото бражается и общая сумма по размерности.

Размерности можно менять местами и перемещать с вертикали на горизон таль и обратно. Для этого можно выбрать команду Moved to Column Area из всплывающего меню кнопки. Во время выполнения можно использовать обычное перетаскивание кнопок при помощи мыши.

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

Таблица 30.6. Свойства и методы компонента TDecisionPivot Объявление Тип ! Описание Свойства property DecisionSource: | j Определяет компонент | | TDecisionSource, через который | | осуществляется управление | ным представлением данных Глава 30. Многомерное представление данных Таблица 30.6 (окончание) Объявление Тип ! Описание type Pb i Задает способ расположения кнопок TDecisionButtonPosition = | на панели:

(xtHorizontal, xtVertical, 1 • xtHorizontal — в ряд слева направо;

xtVertical — в колонку сверху вниз;

property TDecisionButtonPosition;

— кнопки вертикальных | размерностей вдоль верхнего края, I кнопки горизонтальных размер ностей вдоль левого края, кнопка i сумм в левом верхнем углу type Pb i Управляет видимостью трех групп кнопок TDecisionPivotOption = (xtRows, TDecisionPivotOptions = set of TDecisionPivotOption;

property property GroupSpacing: | Определяет размер в пикселах Integer;

промежутка между группами кнопок Методы procedure I Переустанавливает размеры компонента Top, Height, Width: | в соответствии с параметрами метода Integer);

override;

Методы-обработчики компонента унаследованы от класса Пример многомерного представления данных В качестве примера использования многомерного представления данных рассмотрим демонстрационное приложение 30.5).

В качестве исходного набора данных используется запрос к таблицам SALES и CUSTOMER общедоступной базы данных в со ставе поставки InterBase следующего вида:

SELECT FROM SALES S INNER JOIN CUSTOMER С ON = GROUP BY DATE Часть VII. Технологии программирования Запрос удовлетворяет всем требованиям для обеспечения многомерного представления данных. Для выполнения запроса и создания набора данных В проекте существует компонент Набор данных компонента открыт во время разработки, поэтому все ком поненты многомерного представления в проекте ведут себя так же, как и во время выполнения программы.

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

:= DecisionQueryl;

Buttle. Griffith and Со Central Bank DT Systems. LTD.

0, Dallas Technologies Intelligence 0. 30.5. Главная форма проекта Компонент DecisionCubei выполняет всю работу по созданию многомерного представления набора данных компонента DecisionQueryl. Причем, практи чески все делается без вмешательства пользователя.

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

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

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

Дополнительного программного кода проект не имеет.

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

ГЛАВА Использование возможностей Shell API Разобравшись с механизмами вам наверняка захочется "испытать ра дость общения" с объектами, имеющимися в составе ОС. Microsoft уверенно идет к тому, чтобы все составные части своих операционных систем, как и прочих продуктов, превратить в СОМ-объекты. В этом направлении сдела ны большие шаги, и оболочка Windows, и ее файловая система предостав ляют интерфейсы В Windows 2000, судя по заверениям представите лей фирмы, все новые возможности представлены и доступны в виде интер фейсов.

В качестве примера работы с интерфейсом ShellLink вместе с Delphi постав ляется приложение Virtual ListView. Но, во-первых, в нем безо всякого до кументирования вводятся достаточно сложные структуры и интерфейсы;

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

В этой главе мы постараемся объяснить применяемые там приемы.

( Примечание Интерфейсы функций и СОМ-объектов содержатся в модулях SHELLAPI.PAS и которые имеются в поставке Delphi.

Понятие пространства имен Необходимость как-то упорядочить все те сущности, с которыми имеет дело современная ОС, всегда вставала перед разработчиками. Довольно успеш ный подход к этому реализован в платформе Windows. Вооружившись идея ми объектного подхода, в Microsoft разбили интерфейс ОС на две части:

средства поддержки пространства имен и средства его просмотра.

Под пространством имен оболочки (Shell Namespace) мы будем понимать иерархически упорядоченную совокупность имен всех объектов, которые Глава 31. Использование возможностей Shell могут быть просмотрены через средства просмотра — файлы, устройства памяти, принтеры, сетевые ресурсы. В этой совокупности могут встречаться как реально существующие объекты (папки файловой системы), так и вир туальные объекты (папки Принтеры, Мой компьютер и т. п.). Типовым средством просмотра пространства имен является Explorer (Проводник), но можно заменить его на другое средство, в том числе собственноручно раз работанное. Обе составные части являются совокупностями СОМ-объектов, они обладают полиморфизмом и легко расширяемы. Об использовании этих объектов и функций API оболочки ОС и пойдет речь в данной главе.

Размещение значка приложения на System Tray Часто программисту приходится сталкиваться с задачей написания прило жения, работающего в фоновом режиме и не нуждающегося в месте на Па нели задач. Если вы посмотрите на правый нижний угол рабочего стола Windows, то наверняка найдете там приложения, для которых эта проблема решена: часы, переключатель раскладок клавиатуры, регулятор громкости и т. п. Ясно, что, как бы вы не увеличивали и не уменьшали формы своего приложения, попасть туда обычным путем не удастся. Способ для этого предоставляет Shell API.

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

Весь API System состоит из 1 (одной) функции:

function DWORD;

BOOL;

= TNotifylconData;

= record cbSize: DWORD;

Wnd: HWND;

UINT;

uFlags: UINT;

UINT;

szTip: array [0..63] of AnsiChar;

end;

Параметр определяет одну из операций: означает добав ление значка в область, NIM_DELETE — удаление, — изменение.

25 Зак. 754 Часть VII. Технологии программирования Ход операции зависит от того, какие поля структуры TNotifyiconData будут заполнены.

Обязательным для заполнения является поле cbsize — там содержится раз мер структуры. Поле должно содержать дескриптор окна, которое будет оповещаться о событиях, связанных со значком. Идентификатор сообщения Windows, которое вы хотите получать от системы о перемещениях мыши над значком, запишите в поле Если вы хотите, чтобы при этих перемещениях над вашим значком показывалась подсказка, то задайте ее текст в поле szTip. В поле задается номер значка — каждое приложе ние может поместить на System Tray сколько угодно значков. Дальнейшие операции вы будете производить, задавая этот номер. Дескриптор помещае мого значка должен быть задан в поле Здесь вы можете задать зна чок, связанный с вашим приложением, или загрузить свой — из ресурсов.

( Примечание Изменить главный значок приложения можно в диалоговом окне Project/ Options на странице Application. Он будет доступен через свойство Тут же можно отредактировать и строку для — свойство Наконец, в поле вы должны сообщить системе, что именно вы от нее хотите, ИЛИ, другими словами, какие ИЗ полей uCailbackMessage и szTip вы на самом деле заполнили. В этом поле предусмотрена комбинация трех флагов: NIF_ICON, И ВЫ можете заполнить, скажем, поле szTip, но если вы при этом не установили флаг созданный вами значок не будет иметь строки с подсказкой.

Два приведенных ниже метода иллюстрируют сказанное. Первый из них создает значок на System а второй — уничтожает его.

const = + 123;

procedure ;

var nidata : TNotifyiconData;

begin with nidata do begin cbSize := ;

Wnd := := n;

or or hlcon := szTip := 'THis is Example';

end;

Глава 31. Использование возможностей Shell API Shell_NotifyIcon(NIM_ADD, @nidata);

end;

procedure var nidata : TNotifylconData;

begin with nidata do begin cbSize := := uID := n;

end;

end;

Примечание забывайте уничтожать созданные вами значки на System Tray. Это не де лается автоматически даже при закрытии приложения. Значок будет удален только после перезагрузки системы.

Внешний вид значка, помещенного нами на System ничем не отлича ется от значков других приложений (рис. 31.1).

31.1. Над значком, помещенным на панель System Tray, видна строка подсказки Сообщение, задаваемое в поле по сути дела является единственной ниточкой, связывающей вас со значком после его создания.

Оно объединяет в себе несколько сообщений. Когда к вам пришло такое сообщение (в примере, рассмотренном выше, оно имеет идентификатор ПОЛЯ В переданной в обработчик структуре типа распределены так. Параметр содержит номер значка (тот самый, что задавался в поле при создании), а параметр LParam — идентификатор сообщения от мыши, вроде и т. п. К сожале нию, остальная информация из этих сообщений теряется. Координаты мы ши в момент события придется узнать, вызвав функцию API GetCursorPos:

procedure TMessage);

var P : TPoint;

begin case of 756 Часть VII. Технологии программирования begin Popup ;

end;

:

end;

end;

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

Теперь решим еще две задачи. Во-первых, как сделать, чтобы приложение минимизировалось не на Панель задач (TaskBar), а на System Tray? И более того — как сразу запустить его в минимизированном виде, а показывать главную форму только по наступлении определенного события (приходу почты, наступлению определенного времени и т. п.).

Ответ на первый вопрос очевиден. Если минимизировать не только окно ГЛаВНОЙ формы НО И ОКНО ложения то приложение полностью исчезнет "с экра нов радаров". В этот самый момент нужно создать значок на панели System В его всплывающем меню должен быть пункт, при выборе которого оба окна восстанавливаются, а значок удаляется.

Чтобы приложение запустилось сразу в минимизированном виде и без глав ной формы, следует к вышесказанному добавить установку свойства в значение False. Здесь возникает одна ность — если главная форма создавалась в невидимом состоянии, ее ком поненты будут также созданы невидимыми. Поэтому при первом ее показе установим их свойство visible в значение True. Чтобы не повторять это дважды, установим флаг — глобальную переменную procedure TForml.HideMainForm;

begin Appiication.showMainForm := False;

;

end;

procedure var i,j : Integer;

begin Appiication.showMainForm := True;

Глава 31. Использование возможностей Shell API if not then begin for I := 0 to -1 do if is then with as TWinControl do if Visible then begin ShowWindow (Handle, ;

for J := 0 to ComponentCount -1 do if is TWinControl then as end;

ShownOnce := True;

end;

end;

procedure TMessage);

begin inherited;

if (Msg.wParam=SC_MINIMIZE) then begin HideMainForm;

;

end;

end;

procedure begin end;

Теперь у вас в руках полноценный набор средств для работы с панелью System В заключение необходимо добавить, что все описанное реали зуется не в операционной системе, а в оболочке ОС — Проводнике (Explorer). В принципе, и Windows NT 4/2000, и Windows 95/98 допускают замену оболочки ОС на другие, например DashBoard или LightStep. Там функции панели System Tray могут быть не реализованы или реализованы через другие API. Впрочем, случаи замены оболочки достаточно редки.

758 Часть VII. Технологии программирования Интерфейс Этот интерфейс представляет собой средство для создания и управления ярлыками (shortcuts). Все читатели этой главы наверняка создавали и пере мещали ярлыки для наиболее нужных программ, файлов и папок — на ра бочем столе, в главном меню и т. д. С точки зрения ОС эти действия — не что иное, как создание и изменение свойств СОМ-объекта.

Каждый ярлык содержит следующую информацию:

путь к объекту, на который ссылается ярлык (Path);

рабочий каталог для этого объекта (Working Directory);

список параметров, передаваемый объекту при его активизации (Arguments);

начальное состояние окна, соответствующего объекту (нормальное, ми нимизированное, максимизированное) путь к значку, соответствующему объекту (Icon Location);

описание объекта (Description);

сочетание "горячих" клавиш (HotKey).

Для всех этих свойств ярлыка в интерфейсе дано по паре методов — один для чтения, другой для установки значения:

IShellLink = { } [SID_IShellLinkA] function GetPath(pszFile: cchMaxPath: Integer;

var fFlags: DWORD): HResult;

stdcall;

function HResult;

stdcall;

function PItemlDList): HResult;

stdcall;

function GetDescription(pszName: PAnsiChar;

Integer):

HResult;

stdcall;

function PAnsiChar): HResult;

stdcall;

function PAnsiChar;

cchMaxPath: Integer):

HResult;

stdcall;

function PAnsiChar): HResult;

stdcall;

function PAnsiChar;

cchMaxPath: Integer):

HResult;

stdcall;

function PAnsiChar): HResult;

stdcall;

function Word): HResult;

stdcall;

function Word): HResult;

stdcall;

function Integer): HResult;

stdcall;

function SetShowCmd(iShowCmd: Integer): HResult;

stdcall;

function GetIconLocation(pszIconPath: PAnsiChar;

Integer;

out Integer): HResult;

stdcall;

Глава 31. Использование возможностей Shell function PAnsiChar;

Integer):

stdcall;

function SetRelativePath(pszPathRel: PAnsiChar;

dwReserved: DWORD):

HResult;

stdcall;

function HWND;

fFlags: DWORD): HResult;

stdcall;

function SetPath(pszFile: PAnsiChar): HResult;

stdcall;

end;

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

procedure TObject);

var NewLink : IShellLink;

fn, fp : string;

ws : WideString;

hRes : THandle;

pf : IPersistFile;

begin NewLink := as IShellLink;

fn := fp ExtractFilePath(fn);

ws := hRes := ;

if then, False);

end;

В этом примере помимо IShellLink нужно получить доступ к интерфейсу IPersistFile, который "умеет" записывать данные. Задав параметры ярлыка, мы записываем его на диск. При этом проверяется тот факт, что созданный нами объект поддерживает интерфейс IPersistFile. Если указатель на этот интерфейс получен, вызывается его метод save.

Среди перечисленных выше методов IShellLink особое внимание уделим методу Resolve. Он понадобится вам при получении указателя на интерфейс уже существующих ярлыков. Windows пытается вести себя "разумно" и от слеживает перемещения и переименования объекта, на который указывает существующий IShellLink. Но если вы записали содержимое ярлыка в по ток (или на диск), то отследить соответствие ярлыка объекту должны сами, вызвав метод Resolve. Если объект, на который ссылается ярлык, по прежнему находится на своем месте, метод немедленно завершается с нор 760 Часть VII. Технологии программирования мальным кодом возврата. Если файл или объект перемещен или переимено ван, начинается его поиск (рис. 31.2).

Missing Shortcut Windows is searching for to locate file yourself, click 31.2. Поиск объекта, на который указывает ярлык Знакомая картина, не правда ли? Особенно часто она наблюдается в том случае, если пользователь не выработал у себя привычки правильно деин сталлировать раздобытый где-то "софт", стирая его "по старинке". Между тем, за привычным диалоговым окном на рисунке стоит вызов метода Resolve. Если в пределах досягаемости поиска окажется файл с тем же именем и размерами, ярлык будет автоматически переадресован на него;

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

Если вы внимательно изучили рабочий стол своего компьютера, то должны были заметить там ярлыки, ссылающиеся не на файлы, а на специальные объекты "Мой компьютер", "Сетевое окружение", "Принтеры" и т. п. Что бы создать такой ярлык самому, нужно обращение к методу В качестве параметра ему передается структура О том, где ее взять и как заполнить, рассказано в следующем разделе.

Интерфейс Этот интерфейс соответствует папке — одному из основных элементов про странства имен Проводника. Зачем было вводить термин "папка", когда су ществовали уже общепринятые "каталог" и "директория"? В отличие от по следних двух, папка может быть не просто обычным элементом файловой системы. Она может быть виртуальной — как папки Принтеры, Документы или Панель управления. Любая папка может содержать коллекцию объектов из состава пространства имен.

Получив указатель на интерфейс соответствующий папке, вы можете работать с ней, как с объектом "Верхушкой" (корневой пап Глава 31. Использование возможностей Shell API кой) пространства имен является папка Рабочий стол (Desktop). Получить интерфейс isheiiFoider этой папки можно путем вызова функции:

function ppshf: HResult;

Логика работы с описываемым интерфейсом такова: сначала необходимо получить интерфейс нужной папки, а затем можно переходить к работе с ее содержимым. Содержимое представляет собой список, а каждый элемент папки представлен структурой Эта структура не типизирована;

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

( Примечание Все служебные функции работы со структурами PitemiDList — создание, уничтожение, копирование, перемещение по цепочке и т. п. — содержатся в примере Virtual ListView, поставляемом с Delphi. Если вы намерены писать про граммы, работающие с isheiiFoider, целесообразно взять их на заметку.

В дальнейшем для простоты эти структуры будем именовать Рассмотрим функции интерфейса isheiiFoider. Под "текущей папкой" в табл. 31.1 понимается та папка, которая в данный момент представляет Таблица 31.1. Функции интерфейса isheiiFoider Метод Описание function Эта функция позволяет получить pbcReserved: Pointer;

указатель на элемент ppidl, зная lpszDisplayName: POLESTR;

out только его полное имя (с путем) pchEaten: out lpszDisplayName PitemiDList;

var ULONG): HResult;

Возвращает указатель на специаль function HWND;

DWORD;

out ный интерфейс IEnumlDList, пред HResult;

назначенный для организации цикла по всем элементам списка в текущей папке function Возвращает интерфейс папки PitemiDList;

pbcReserved: Pointer;

которая должна находиться в теку const riid: out ppvOut: щей папке (на которую ссылается Pointer): HResult;

интерфейс, вызвавший этот метод) function Сравнивает два первых элемента pidl2: PitemiDList): HResult;

в списках pidll и pidl 762 Часть VII. Технологии программирования Таблица (окончание) Метод Описание function Создает визуальный объект для HWND;

const riid: out ppvOut: текущей папки и возвращает указа Pointer):

тель на него в параметре ppvOut function UINT;

Возвращает атрибуты элемента var PItemlDList;

под номером cidl в списке apidl.

var UINT): HResult;

Результат — набор флагов, устанав ливаемых в параметре function Создает объект пользовательского HWND;

cidl: UINT;

var apidl:

интерфейса, связанный с элементом PItemlDList;

const riid: TIID;

списка aplidl под номером cidl Pointer;

out ppvOut:

Pointer): HResult;

function Возвращает имя элемента pidl.

PItemlDList;

uFlags: DWORD;

Полнота возвращаемой информации var TStrRet): HResult;

определяется параметром uFlags function HWND;

Задает новое имя для pidl: PItemlDList;

lpszName:

списка pidl. При этом возвращается POLEStr;

uFlags: DWORD;

новый указатель на список — var ppidlOut: PItemlDList): HResult;

ppidlOut Два — И GetDisplayNameOf — взаимно ДОПОЛНЯЮТ друг друга. Первый из них нужен, если вы имеете указатель на и хотите связать его с конкретной папкой. На практике это сводится к зада че в три действия:

1. Получить указатель на интерфейс какой-либо папки, скажем, рабочего СТОЛа, При ПОМОЩИ ShGetDesktopFolder.

2. Получить указатель (pidl) нужного вам элемента. Это осуществимо мно гими способами. Первый из них — как раз через вызов метода IShellFolder. ParseDisplayName. Если ВЫ хотите получить доступ К ОДНОЙ из виртуальных (специальных) папок, то незаменимой будет следующая функция:

function HWND;

nFolder: Integer;

var PItemlDList): HResult;

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

Глава 31. Использование возможностей Shell API Примечание Во многих функциях Shell API и методах его интерфейсов встречается пара метр hwndOwner. Он должен задавать дескриптор окна на тот случай, если при дется выводить диалоговое окно или окно с сообщением об ошибке.

Возможные значения параметра перечислены в табл. 31.2. В ком ментариях к ним "виртуальная" папка является особым объектом, кото рый предоставляется пользователю при помощи Shell API. Просто "пап ка" реально существует где-то в файловой системе.

Таблица 31.2. Константы, определяющие специальные папки Значение Комментарий Корзина (Recycle bin) — специальная папка для удаленных файлов. Пути к Recycle bin нет в сис темном реестре во избежание перемещения или удаления, и его не узнать иным методом CONTROLS Панель инструментов (Control Panel) — виртуаль ная папка, содержащая значки апплетов Панели инструментов CSIDL DESKTOP Виртуальная папка Рабочий стол (Desktop), кор невая в пространстве имен CSIDL DESKTOPDIRECTORY Папка файловой системы, реально содержащая объекты рабочего стола CSIDL DRIVES Виртуальная папка Мой компьютер (My Computer), содержащая элементы для всех накопителей на компьютере подключенных сетевых устройств, пап ки Принтеры, Панель инструментов, Удаленный доступ к сети Виртуальная папка Шрифты Папка, содержащая объекты сетевого окружения Виртуальная папка Сетевое окружение (Network Neighborhood) Папка Мои документы CSIDL_PRINTERS Виртуальная папка Принтеры (Printers) Папка Программы из главного меню, содержащая папки установленных на компьютере программ Папка, содержащая ссылки на последние исполь зовавшиеся документы (Recent) CSIDL SENDTO Папка, содержащая элементы контекстного меню Часть VII. Технологии программирования Таблица 31.2 (окончание) Значение Комментарий Папка, содержащая элементы главного меню Пуск (Start) STARTUP Папка, содержащая элементы меню Автозапуск (Startup) CSIDL TEMPLATES Папка, содержащая шаблоны типовых документов Третий вариант получить нужной папки — интерактивный, с по мощью функции Shell function Перед ее вызовом следует заполнить структуру типа содер жащую в частности того элемента, который будет корневым. После вызова функции пользователь увидит перед собой диалоговое окно вы бора папки (рис.

browse for Folder Desktop !- My Computer '+ 3 5 (A:) ( _J Documents and Settings r _J Inetpub t Inprise 1, Mark _J Petr Program Files.

. • " ' • •... • :.

•. •.. •. • • • • • • • • : •...

•••, C a n c e l 31.3. Диалоговое окно выбора папки, созданное при вызове функции ShBrowseForFolder В данном примере корневой служит виртуальная папка My Computer.

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

Глава 31. Использование возможностей Shell API procedure TObject);

var :

Image : integer;

StartPIDL, ResPIDL :

S, Path : Of begin StartPIDL));

With BI do Begin hwndOwner • = = @S;

lpszTitle = 'Выберите необходимую папку';

ulFlags = pidlRoot = StartPIDL;

= nil;

end;

ResPIDL := if @Path[0]) then := end;

Полученное имя здесь отображается при помощи компонента Labeii.

3. Наконец, перейдем к третьему действию нашей задачи. Теперь, зная папки, с которой вы будете работать, можно получить указатель на ин терфейс вызовом метода BindToObject. Мы еще не рассмот рели такой важный аспект работы с папками, как просмотр их содержи мого. Верные правилу "каждый должен заниматься своим делом", разработчики Shell предоставили для просмотра еще один интерфейс — Пугаться нечего, набор возможностей этого интерфейса да же меньше, чем у пульта ДУ в магнитофоне. Его четыре метода — Next, Reset и clone — позволяют организовать просмотр списка в направлении, а также возврат к началу и дублирование (Clone) выбран ного элемента списка. Вот как это выглядит на практике.

try if not (Editl.Text,ws, MAX_PATH),n, attr)) Часть VII. Технологии программирования then begin имя');

Exit;

end;

IID_IShellFolder, or Enumerator));

while pidl, Numpidls) = do begin StrRet);

case of STRRET_CSTR:

s := begin P := SetString(s, P, end;

s := end;

//case end;

except on E:E01eSysError do end;

В этом примере имя нужной папки извлекается из компонента Получив указатель на интерфейс и затем интерфейс программа заполняет полученными именами файлов список Помимо названия из большинства объектов файловой системы можно "вы тащить" массу полезной информации. Чаще всего задаются вопросом: а как извлечь значок, соответствующий данному файлу или хранящийся в нем?

Способов для достижения этой цели несколько. Самый простой — через вызов функции:

function PAnsiChar;

DWORD;

var psfi: DWORD;

Параметр pszPath может быть указателем как на строку с именем файла, так и на структуру вида pidl. Функция заполняет структуру psfi (тип TSHFilelnfo) длиной байт. В зависимости от значения слова фла гов (параметр uFlags) на выходе может быть разнообразная информация.

В частности, если в параметре uFlags заданы значения SHGFI_SYSICONINDEX И SHGFI_ICON, то в структуру psfi будет записан номер значка для данного Глава 31. Использование возможностей Shell API файла в системном списке изображений, а результатом выполнения функ ции будет дескриптор этого списка. Воспользоваться им можно (например, для панели инструментов) так:

procedure var THandle;

begin ImageListHandle := 0, Filelnfo, or 0, ImageListHandle);

end;

Точно так же можно извлечь значок, соответствующий конкретному файлу.

В составе Shell есть другие функции, созданные для извлечения значков:

function PChar;

Эта функция извлекает значок из файла lpszExeFileName (это должен быть файл типа EXE, DLL или и возвращает его дескриптор. Если значок не найден, возвращаемое значение равно 0.

function HINST;

lpIconPath: PChar;

var Word): HICON;

Эта функция может работать с файлами разных форматов. Сначала она, как и предыдущая, ищет значок в теле файла. Если его там нет, пред принимается попытка отыскать значок в приложении, связанном с дан ным типом файлов. Например, из файла с расширением будет из влечен один из значков Microsoft Word.

Добавление пунктов в системное контекстное меню Вы обращали внимание на то, что некоторые приложения после установки добавляют в системное контекстное меню свои собственные пункты? Так поступают многие архиваторы, антивирусные средства и другие утилиты.

Эта возможность предоставляется оболочкой Windows.

Когда пользователь щелкает правой кнопкой мыши на любом объекте в пространстве имен, система создает контекстное меню из двух частей: стан дартного меню для объектов данного типа и пунктов меню, добавляемых Часть VII. Технологии программирования зарегистрированными обработчиками. Зарегистрированные обработчики — это СОМ-серверы, запускаемые в адресном пространстве процесса (in process servers) и реализованные в виде динамических библиотек.

Ваш СОМ-объект, который расширяет системное контекстное меню, дол жен поддерживать как минимум два интерфейса — и Существуют и два новых интерфейса — и но они вносят в логику работы контекстных меню лишь не большие дополнения и здесь рассмотрены не будут. Интерфейс isheliExtinit отвечает за инициализацию меню, а интерфейс — за выполне ние основных Методы интерфейса IContextMenu приведены в табл. 31.3.

Таблица 31.3. Методы интерфейса Метод Описание function QueryContextMenu (Menu: HMENU;

Добавляет пункт к системному indexMenu, контекстному меню uFlags: stdcall;

function Осуществляет вызов обработчика : HResult;

stdcall;

function Возвращает описание добавлен uType: UINT;

pwReserved: ного пункта меню (подсказку или LPSTR;

cchMax: UINT): полное название) HResult;

stdcall;

Рассмотрим их подробнее. Параметры метода QueryContextMenu означают следующее:

Menu — дескриптор системного меню;

indexMenu — позиция в меню, в которую следует вставить пункт (пункты);

idCmdFirst, idCmdLast — диапазон допустимых значений для идентифика торов вставляемых пунктов меню;

uFlags — набор флагов, главные из которых означают:

• CMF_NORMAL — обычный вызов контекстного меню, пункты могут быть добавлены. Значение этого флага нулевое, проверять его следует, очи стив все биты в параметре uFlags, кроме пяти младших (маска $1F);

• CMF_DEFAULTONLY — устанавливается, если пользователь задал с объек том действие по умолчанию (например, двойной щелчок). В этом слу чае пункты меню добавляться не должны;

Глава 31, Использование возможностей Shell API • — устанавливается, если меню создается для ярлыка объекта, а не для самого объекта. В этом случае многие пункты меню создаваться не должны;

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

Для иллюстрации объектов — расширений контекстного меню — выберем пример ContMenu (поставляется с Delphi в папке \SHELLEXT). В этом примере для объектов типа "проект Delphi" добавляет ся возможность запуска компилятора в командной строке. При вызове метода нужный пункт добавляется с помощью функции InsertMenu:

function indexMenu, idCmdFirst, uFlags: HResult;

begin Result := 0;

// или использовать // FACILITY_NULL, 0);

if ((uFlags and $0000000F) = or ((uFlags and <> 0) then begin // Добавить один пункт меню во всплывающее меню indexMenu, MF_STRING or idCmdFirst, 'Compile...');

Result := 1;

// или использовать // FACILITY_NULL, 1) end;

end;

Метод Getcommandstring предоставляет системе данные о пункте меню, в частности, текст подсказки;

эта подсказка будет отображаться в строке состояния Проводника, когда курсор находится в нужном месте меню.

Параметры Getcommandstring просты. Первый — idcmd — соответствует иден тификатору пункта меню, второй — итуре — запрос на тип информации (GCS_HELPTEXT — текст подсказки, GCS_VERB — полное название пункта ме ню). Наконец, параметры pszName и задают буфер, в который будут копироваться текстовые данные. Полное название необходимо системе, чтобы с его помощью вызывать предусмотренные в пункте действия про граммно. В примере ContMenu возврат названия (т. е. обработка запроса GCS_VERB) не предусмотрен, а в ответ на запрос GCS_HELPTEXT возвращается строка "Compile the selected Delphi project".

Наиболее сложным является метод invokeCommand. Он вызывается при выбо ре пользователем вставленного вами пункта меню. По сути дела метод представляет собой прямой аналог обработчика onclick обыч ных пунктов меню (объектов в Delphi.

770 Часть VII. Технологии программирования Единственным параметром метода является структура типа поля которой имеют такое предназначение:

cbsize — размер структуры в байтах;

— задает дескриптор окна, которое будет владельцем диалоговых окон, вызываемых из метода;

— определяет, заданы ли параметры lpverb — вызываемая команда;

lpParameters — параметры (если есть);

• — рабочая папка (поле не обязательно);

— флаг состояния окна, который будет передан в функцию dwHotKey — "горячая" комбинация клавиш, которая будет сопоставляться приложению, запускаемому из этого пункта меню (только если в пара метре установлен флаг CMIC_MASK_HOTKEY);

— значок, который будет сопоставляться приложению, запускае мому из этого пункта меню (только если в параметре fMask установлен флаг — монитор по умолчанию (поле не обязательно).

Отдельно следует остановиться на описании параметра lpverb. Как уже го ворилось, он может представлять из себя как идентификатор пункта меню, так и его текст — строку, заканчивающуюся нулем. Чтобы выяснить это, нужно проверить старшее слово этого 32-разрядного параметра на равенство нулю. В примере ContMenu вызов по тексту не предусмотрен:

if о 0) then begin Exit ;

end;

Для создания расширения контекстного меню мы должны породить объект, поддерживающий эти интерфейсы. К сожалению, мастера, предусмотрен ные в Delphi, не позволяют в автоматизированном режиме создавать объек ты, реализующие уже существующие интерфейсы. Поэтому и описание, и реализацию методов придется делать "по старинке", вручную. В примере ContMenu описание объекта таково:

TContextMenu = IContextMenu) private of Char;

protected { IShellExtlnit } Глава 31. Использование возможностей Shell API function = SEIInitialize;

function IDataObject;

HKEY): stdcall;

{ IContextMenu } function QueryContextMenu(Menu:

idCmdLast, uFlags: HResult;

stdcall;

function HResult;

stdcall;

function uType: UINT;

pwReserved:

LPSTR;

UINT): HResult;

stdcall;

end;

Вас может насторожить конструкция, описывающая переименование метода initialize интерфейса На самом деле одноименный метод имеется у объекта TComObject, и приведенный синтаксис как раз и предна значен для выхода из подобных ситуаций.

Последняя часть работы — регистрация созданного обработчика. Самое подходящее место для этого — метод updateRegistry фабрики класса. Разра ботчики ПОРОДИЛИ КЛаСС TContextMenuFactory, КОТОрЫЙ при регистрации СОМ-сервера регистрирует создаваемые фабрикой объекты:

ClassID := '', '', '') ;

ClassID);

Пример ContMenu иллюстрирует "дельфийский" подход к созданию серве ров через соответствующие объекты из иерархии объектов Delphi. Но в папке SHELLEXT вы найдете еще один пример создания расширения для контекстного меню, сделанный целиком и только с использованием интер фейсов и функций Присмотритесь к этому примеру внимательнее, если хотите глубже понимать внутреннюю структуру СОМ-объектов.

Резюме Несколько тем, затронутых в этой главе, могут дать лишь начальные пред ставления о принципах работы с оболочкой Windows. Вы можете изучить составляющие ее объекты практически сколь угодно глубоко — бы потребность да желание. Разумеется, чтобы не "наломать дров", перед этим надо отдать себе отчет в полном и правильном понимании механизмов ПРИЛОЖЕНИЕ Описание дискеты Уважаемый читатель!

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

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

Некоторые приложения используют в качестве источника данных демонст рационную базу данных Delphi, которая при стандартной инсталляции на ходится в папке \Program Files\Barland Shared\Data. При ра боте с такими приложениями вам необходимо самостоятельно настроить соответствующие свойства компонентов доступа к данным. Они преднаме ренно обнулены, т. к. на вашем компьютере база данных Delphi может рас полагаться в другом месте.

В приложениях, использующих генератор отчетов Rave Reports, в компонен те TRvProject необходимо указать полный путь к файлу проекта RAV, по скольку, хотя этот файл и располагается в папке приложения, отсутствие полного пути может приводить к ошибке.

Ниже приводится описание демонстрационных приложений.

Папка Приложение 05_1 Пример использования компонентов TTreeView и TTreeList для про смотра информации из системного реестра Windows 05_2 Простой пример разработки собственного компонента 06_1 Ресурсы манифеста Windows 07_1 Пример использования в приложении списка объектов на основе класса Приложение (продолжение) Папка Приложение 07_2 Пример использования в приложении списка строк на основе класса 10_1 Пример приложения, использующего компоненты Delphi для отображе ния графики 10_2 Приложение для просмотра растровых приложений JPG, JPEG, BMP Пример простейшего приложения баз данных 12_1 Пример использования параметров компонентов запросов SQL и взаи модействия таких компонентов на основе передачи значений пара метров 14_1 Приложение баз данных, использующее отношение "один-ко-многим" между таблицами базы данных 14_2 Приложение баз данных, демонстрирующее варианты поиска записей в таблице базы данных 14_3 Пример использования закладок (класс в наборах данных Delphi 15_1 Приложение баз данных, использующее компоненты синхронного про смотра Приложение баз данных, напрямую использующее API BDE для полного удаления записей из таблиц базы данных 16_2 Приложение баз данных, напрямую использующее API BDE для пред ставления данных 17_1 Приложение баз данных, демонстрирующее возможности технологии 19_1 Приложение баз данных, демонстрирующее возможности технологии ADO 21_1 Пример простого распределенного приложения баз данных 25_1 Пример использования компонента проекта отчета Rave Reports и раз работки простых отчетов в визуальной среде Rave Reports 26_1 Пример использования настраиваемого соединения на основе компо нента 26_2 Пример отчетов Rave Reports для приложений баз данных 27_1 Пример реализации Drag-and-Drop 27_2 Пример реализации Drag-and-Dock 27_3 Пример реализации управления мышью 28_1 Пример создания динамической библиотеки Описание дискеты (окончание) Папка Приложение 29_1 Приложение, использующее отдельный поток к памяти для расчета числа 30_1 Приложение, использующее компоненты многомерного представления данных _1 Пример приложения, использующего Shell API Предметный указатель dynamic 28, А Dynamic Method Table Abort Action E Action client Action target ADO API BDE Error EFOpenError В BDE Event brcc32.exe ExceptAddr Exception С ExceptObject Comctl32.dll • Critical section IAccessor IAppServer 555, 558, D IColumnsInfo DataSnap 570, dbExpress ICommandPrepare default 22 Device Dependent Bitmap Device Independent Bitmap ICommandWithParameters DLL PROCESS ATTACH IConvertType DLL PROCESS DETACH DLL THREAD ATTACH IDBInitialize DLL_THREAD_DETACH IDBProperties Drag-and-Dock 669 inherited 19, Drag-and-Drop Предметный указатель IOResult С IProviderSupport IRowset Self 17, IRowsetChange Semaphore Sender ShowException SQL Links IRowsetLocate IRowsetUpdate T TAction 175, IShellLink TActionList TADOConnection ISQLConnection TADODataSet ISQLCursor ISQLDriver TADOStoredProc ITransaction TADOTable ITransactionLocal TBDEDataSet ITransactionObject TBitmap TBrush TCanvas 63, J TCaption JPEG 243 TChart TClass TClientDataSet 572, M TCollection Microsoft ActiveX Data Objects Mutex TColor TCommonCalendar О OLE DB TConnectionBroker OnException TControl overload TControlState override TControlStyle TCORBADataModule P private 35 TCursor property 20 TCustomADODataSet protected 36 TCustomClientDataSet public 35 TCustomControl published 36 TCustomTabControl TDatabase R 281, 305, TDataSetField raise 68, 72, TDataSetProvider 545, 554, reintroduce 778 Предметный указатель 269, 274, 300, 371 TDateTimePicker 127 TList TDBChart 365 TLocalConnection 366 359 TMonthCalendar TDBGrid 349 TMTSDataModule 349 TNotifyEvent 367 41, TDBListBox 366 TOpenPictureDialog 372 TPageControl 369 ListBox 372 367 TPen TDBNavigator 277, 362 TPicture TDBRadioGroup 366 368 TRect TDBText TDCOMConnection TRvNDRWriter TDecisionCube 736, 602, TDecisionGraph 744, TRvRenderHTML TDecisionGrid TRvRenderRTF TDecisionPivot 747, TRvRenderText 735, 605, TDecisionSource Dialog TFont 57, TFontDialog TGraphic TSharedConnection THandleStream TSimpleObjectBroker TSOAPDataModule TSocketConnection TIBDatabase 426, 431, TIBDataSet TSQLDataSet TIBEvents TSQLQuery TIBQuery TIBSQL TSQLTable TStandardColorMap TIBStoredProc TStatusBar TIBTable TStatusPanel TIBTransaction TStoredProc TStream TStringList TStrings Предметный указатель V TTable TTabSheet virtual 28, Virtual Method Table Button w TTwilightColorMap widget 88, TWebConnection TWebDataModule TWidgetStyle X TWinControl TXPColorMap XSQLDA TXPManifest XSQLVAR Д Действие Агрегатные поля Делегирование Агрегаты Дескриптор окна Агрегаты-объекты Деструктор Атрибуты файла Диапазон Динамическая библиотека ресурсов Динамические поля Динамический приоритет Базовый приоритет Директива:

Битовая карта 0 pascal Блок защиты ресурсов О register Буфер Delta О 0 В Дочерний класс Драйверы Взаимное исключение 721, Визуальный стиль Виртуальный метод Вложенные наборы данных Внешний провайдер данных Закладка 342, Внутренний провайдер данных Значок Вызовы в DLL Вычисляемое поле И Индекс Инициализация DLL Группировка агрегатов 587 Инкапсуляция Предметный указатель Объект-транзакция ADO К Объекты:

О в списках Кисть О синхронизации Класс тип Клиент многозвенных приложений Ограничения данных Коллекции Опережающее объявление класса Колонка Отложенный ввод/вывод Команда ADO Отношение 334, Компоненты доступа к данным Отображаемый файл Компоненты отображения данных 276, Конструктор п Контекст устройства Конфигурация BDE Пакет данных Критическая 722, Панель инструментов Кросстаб Папка обмена Параметры запроса SQL Первичный индекс 296, м Перо Позднее связывание Манифест Поиск данных Маска Поиск файла Метафайл Поле 17, Метод 17, Полиморфизм О абстрактный Пользовательский интерфейс О виртуальный Потоки 213, О динамический Провайдер ADO 485, О класса Провайдер данных О перегружаемый Проект CLX О статический Проект динамической библиотеки Метод-обработчик событий Процесс Модуль Процессор баз данных Псевдоним базы данных н Набор данных 268, Наследование Родительский класс Неявный вызов DLL Нормальный приоритет Свойство Семафор 721, Область видимости Сервер приложений 533, Обработка исключительных ситуаций Синхронизация потоков Объект Синхронный просмотр данных О поля Ситуация гонок Объект-источник данных ADO Событие 23, ADO Соответствие типов Объект-набор рядов ADO Списки Объект-перечислитель ADO 0 указателей Объект-сессия ADO Предметный указатель Статические поля Фоновые процедуры Страничный файл Фоновый приоритет Функция:

О IOResult О блочного ввода/вывода О ввода/вывода Тема О обратного вызова Типы:

О данных О полей 314, Тонкий клиент Трехзвенная модель Цвет Тупики ш Шрифт 57, Удаленный модуль данных 537, Указатель на метод э Ф Экземпляр класса Экспорт функций DLL Файл DPR Файловые переменные Файлы, отображаемые в память Фильтр 340, Явный вызов DLL Фокус ввода 119991 г. Москва, ул. Губкина, д. soft!

тел.: (095) 232- www.softline.ru e-mail: info@softline.ru Все для разработки ПО Почему опытные разработчики приобретают нужные для их работы программы в компании И Их привлекают низкие цены, т.к. компания работает напрямую с вендо рами.

Ш Их привлекает имеющаяся возможность получения демо-версий и об новлений.

• В выборе программ им помогают каталог SoftLine-direct и сайт • Большая часть ассортимента SoftLine для разработчиков недоступна в других компаниях.

Какие этапы разработки охватывает программное COMPAQ обеспечение, поставляемое SoftLine?

• Проектирование программ (Microsoft, Rational, SilverRun, Quest).

Совместная работа (Centura, Merant, Microsoft).

• Управление проектами PlanView, Microsoft).

Написание кода (среды разработки Allaire, Borland, IBM, Microsoft, ком поненты Allround Automation, ComponentOne, Crystal Decisions, Janus, Stingray).

• Оптимизация кода (Compaq, Fuji, Intel, MainSoft, Sun, Sybase, Tenberry).

• Отладка и тестирование (NuMega, Intuitive Systems, Segue).

• Упаковка приложений (InstallShield, Wise Solutions).

• Развертывание и поддержка (Remedy, RoyalBlue, Network Associates).

• Обучение пользователей (Adobe, Allen Communications, click2learn.com, si t r aka Macromedia, Quest, Ulead).

SoftLine — это свобода выбора Обратившись в SoftLine, вы в кратчайшие сроки решите проблемы с про граммным обеспечением. Получив консультацию менеджеров, часть из ко торых знакома с работой разработчиков не понаслышке (на собственном опыте), вы подберете все необходимое для работы в вашей области — от интегрированной среды RAD — до готовых компонент. При этом мы оста- InstallShield вим выбор идеологии разработки за вами - например, для регулярного получения информации о продуктах и технологиях, вы сможете подписать ся на Microsoft Developer Network, Sun Developer Essentials или на нашу соб ственную рассылку компакт-дисков - SoftLine Support Subscription, предо ставляющую обновления и всех ведущих производителей.

Компания SoftLine также поможет вам в выборе обучающих курсов.

INFORMATION ANYWHERE.

ВЕСЬ МИР компьютерных книг Более 1600 наименований книг в И Н Т Е Р Н Е Т - М А Г А З И Н Е Internet "Остановить | Гочга Ссылки I расширенный поиск--» Как купить книгу страница • Прайс-лист компьютерной Mi crosof t Offi ce • литературы предлагает большой в целом Готовятся к печати добор книг компьютерной тематики.

Расширенный поиск • Электронные книги книг:

книг: Обзоры : Главная страница Издательство Петербург" Справочник Web-мастера.

Петербург" МИР КОМПЬЮТЕРНЫХ КНИГ 1 6 0 КНИГ ПО КОМПЬЮТЕРНОЙ ТЕХНИКЕ, ПРОГРАММНОМУ ОБЕСПЕЧЕНИЮ И ЭЛЕКТРОНИКЕ ВСЕХ РУССКОЯЗЫЧНЫХ ИЗДАТЕЛЬСТВ УВАЖАЕМЫЕ ЧИТАТЕЛИ!

ДЛЯ ВАС ОТКРЫЛСЯ ОТДЕЛ "КНИГА - ПОЧТОЙ" Заказы принимаются:

=> По телефону: 541-85-51 (отдел "Книга — почтой") По факсу: 541 -84-61 (отдел "Книга — почтой") По почте: Санкт-Петербург, а/я => По E-mail:

Если у Вас отсутствует Internet — по почте, БЕСПЛАТНО, высылается дискета с прайс-листом (цены указаны с учетом доставки), аннотациями и оглавлениями к книгам и, конечно, условиями заказа.

Pages:     | 1 |   ...   | 8 | 9 ||



© 2011 www.dissers.ru - «Бесплатная электронная библиотека»

Материалы этого сайта размещены для ознакомления, все права принадлежат их авторам.
Если Вы не согласны с тем, что Ваш материал размещён на этом сайте, пожалуйста, напишите нам, мы в течении 1-2 рабочих дней удалим его.