Электронная библиотека » Александр Чиртик » » онлайн чтение - страница 15


  • Текст добавлен: 10 ноября 2013, 00:08


Автор книги: Александр Чиртик


Жанр: Программирование, Компьютеры


сообщить о неприемлемом содержимом

Текущая страница: 15 (всего у книги 24 страниц)

Шрифт:
- 100% +
Реестр

Далее будет рассмотрено несколько примеров использования в программах на Delphi одного из важнейших хранилищ информации Windows – системного реестра.

Краткие сведения о реестре Windows

Что же представляет собой системный реестр и для чего он предназначен? Реестр состоит из нескольких файлов с довольно сложной организацией записей, формирующих иерархическую структуру (родитель-потомки), а точнее, несколько веток структуры. Благодаря наличию специальных функций пользователь может работать с реестром именно как с иерархической структурой, а не как с набором записей в файле.

Реестр Windows является отличным примером организации централизованного хранения данных, в основном, настроек программ, и хорошей альтернативой большим INI-файлам, доставшимся в наследство от 16-разрядных версий Windows, главным образом, из-за обеспечения возможности лучше структурировать информацию (ведь секции разделов в реестре могут быть много раз вложенными). В реестре хранятся и данные, которые могут пригодиться сразу многим программам: например, расположения COM-серверов, пути приложений, ассоциированных с различными типами файлов.

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

Данные реестра сгруппированы в несколько ветвей (рис. 7.6). Для запуска показанной на рис. 7.6 программы Редактор реестра достаточно набрать в командной строке Regedit либо найти файл Regedit.exe в папке Windows.

Рис. 7.6. Корневые разделы реестра


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

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

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

• HKEY_LOCAL_MACHINE – самая большая и главная ветвь реестра, содержащая параметры Windows, приложений, оборудования, ассоциации расширений файлов, расположение COM-серверов и много другой полезной информации.

• HKEY_CURRENT_CONFIG – в этом разделе хранятся значения параметров Windows, отличающиеся от стандартных. Он является псевдонимом для ветви HKEY_LOCAL_MACHINESYSTEMCurrentControlSetHardware ProfilesCurrent.

• HKEY CLASSES ROOT – в системах Windows 95/98/NT 4.0 и более ранних этот раздел является псевдонимом для ветви HKEY LOCAL MACHINESOFTWAREClasses. В Windows 2000/XP содержимое этого раздела составляется из содержимого разделов HKEY_LOCAL_MACHINESOFTWAREClasses и HKEY_ CURRENT_USERSoftwareClasses.

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

Средства работы с реестром

Для работы с реестром предусмотрена целая группа API-функций. Однако зачем изобретать велосипед, испытывая на себе «удобство» работы с этими функциями, ведь Borland предоставляет замечательный по своей простоте класс TRegistry? Использованию этого класса как раз и посвящено несколько следующих далее абзацев.

Класс TRegistry находится в модуле Registry. Если вам все же станет интересно использование API для работы с реестром, то можете заглянуть в этот модуль и там посмотреть, как реализованы методы класса TRegistry.

Примечание

Помимо TRegistry, в модуле Registry можно найти такие классы, как TRegIniFile и TRegistrylniFile, позволяющие работать с реестром, будто это INI-файл. В ряде случаев использование этих классов вместо TRegistry позволяет сокращать размер программы, да и значительно ее упрощать.

В табл. 7.1 приведены свойства класса TRegistry.

Таблица 7.1. Свойства класса TRegistry

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

• KEY_QUERY_VALUE – получение значений параметров раздела;

• KEY_ENUMERATE_SUB_KEYS – составление списка подразделов;

• KEY_SET_VALUE – задание значений, создание параметров в разделе;

• KEY_CREATE_SUB_KEY – создание подразделов;

• KEY_CREATE_LINK – создание символических ссылок (здесь не рассматривается);

• KEY_NOTIFY – обеспечивает право на уведомление об изменении раздела и его подразделов (здесь не рассматривается);

• KEY_READ – сочетание значений KEY_QUERY_VALUE, KEY_ENUMERATE_SUB_ KEYS и KEY_NOTIFY;

• KEY_WRITE – сочетание значений KEY_SET_VALUE и KEY_CREATE_SUB_KEY;

• KEY_ALL_ACCESS – сочетание значений KEY_READ, KEY_WRITE и KEY_CREATE_LINK.

Приводить список всех методов класса TRegistry в книге нерационально, да и незачем. Благо, названия методов говорят сами за себя (к тому же Delphi поставляется с неплохой справочной системой). Здесь же остановим внимание на рассмотрении некоторых особенностей работы с методами класса TRegistry.

Работая с разделами реестра, важно (в общем случае) соблюдать следующую последовательность.

1. Установить значение свойства RootKey, если корневой раздел отличен от HKEY_CURENT_USER. Установить значение свойства Access, если нужно ограничить доступ.

2. Открыть методом OperKey или создать методом CreateKey раздел реестра. Если использовать OperKeyReadOnly, то задавать значение свойства Access, о котором сказано в пункте 1, не имеет смысла.

3. Произвести нужные операции с элементами раздела.

4. Закрыть раздел, по крайней мере, если вы собираетесь использовать один и тот же объект TRegistry для последовательной работы с несколькими разделами (метод OpenKey не закрывает ранее открытый раздел).

Теперь несколько слов о проверке работы методов класса TRegistry. Большинство методов этого класса, организующих доступ к разделам реестра, реализованы как функции, возвращающие True в случае успеха и False при возникновении ошибки. При этом особо выделяется метод CreateKey, который в случае неудачи генерирует исключение ERegistryException.

Для чтения и записи параметров разного типа в классе TRegistry предусмотрены пары Read– и Write-методов. Использовать их крайне просто, в чем вы убедитесь чуть позже. Главное при использовании этих методов – не забывать определять тип значений параметров, если он заранее вам точно не известен, например, с помощью функции GetDataType. Следует также помнить, что методы работы с параметрами генерируют исключение ERegistryException при возникновении ошибок.

Напоследок о параметре (По умолчанию) – он может присутствовать в каждом разделе. Для обращения к этому параметру используется пустая строка в качестве имени раздела. Нужно только учитывать, что в отличие от более ранних версий Windows в Windows 2000/XP этот параметр автоматически не создается.

Хранение настроек программы в реестре

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

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

Теперь о деле: пусть есть форма для фильтрации запроса к базе данных, показанная на рис. 7.7.

Рис. 7.7. Форма фильтра для поиска товара


Содержимое формы не имеет особого значения – важно то, что при нажатии кнопки OK положение, размер формы, а также данные, введенные пользователем, будут сохранены в реестре с помощью процедуры SaveFilter (листинг 7.14).

Листинг 7.14. Сохранение параметров формы в реестре

procedure TForm1.OKClick(Sender: TObject);

begin

SaveFilter();

//Выполняем требуемые действия...

end;

//Процедура сохраняет параметры в реестр

procedure TForm1.SaveFilter();

var

reg: TRegistry; //По умолчанию: RootKey = HKEY_CURRENT_USER

strShops: String;

i: Integer;

begin

reg:= TRegistry.Create();

try

//Открываем или создаем раздел, в котором будут

//сохранены параметры формы

reg.OpenKey(strBaseKey + 'Form1', True);

//Сохранение параметров

//1. Размер и положение формы

reg.WriteInteger('Width', Width);

reg.WriteInteger('Height', Height);

reg.WriteInteger('Top', Top);

reg.WriteInteger('Left', Left);

//2. Последнее введенное наименование

reg.WriteString('txtName.Text', txtName.Text);

//3. Выбранные магазины

strShops:= '';

for i:= 0 to lstShops.Count–1 do

if lstShops.Selected[i] then

strShops:= strShops + lstShops.Items[i] + ',';

reg.WriteString('lstShops.Selection', strShops);

//4. Применение сортировки

reg.WriteBool('chkSort.Checked', chkSort.Checked);

except

on ERegistryException do

MessageBox(Handle, 'Ошибка при сохранении фильтра ',

'Поиск товара', MB_ICONEXCLAMATION);

end;

reg.CloseKey();

reg.Free();

end;


В рассматриваемом примере константа strBaseKey, определяющая положение раздела для сохранения настроек, задана следующим образом:


const strBasekey = 'SoftwareDelphi. Трюки и эффектыНастройки программы';


Открыв Редактор реестра, можно удостовериться в правильном сохранении параметров (рис. 7.8).

Рис. 7.8. Параметры формы, записанные в реестр


Считывание параметров формы можно выполнять, например, при ее создании. Тогда в обработчик события Create достаточно поместить вызов процедуры LoadFilter (листинг 7.15).

Листинг 7.15. Загрузка параметров формы из реестра

procedure TForm1.FormCreate(Sender: TObject);

begin

LoadFilter();

end;

//Процедура загружает параметры из реестра

procedure TForm1.LoadFilter();

var

reg: TRegistry; //По умолчанию: RootKey = HKEY_CURRENT_USER

strShops: String;

shopStart, shopEnd: Integer;

begin

reg:= TRegistry.Create();

try

//Открываем раздел, в котором сохранены параметры формы

reg.OpenKey(strBaseKey + 'Form1', False);

//Загрузка сохраненных ранее параметров

//1. Размер и положение формы

Width:= reg.ReadInteger('Width');

Height:= reg.ReadInteger('Height');

Top:= reg.ReadInteger('Top');

Left:= reg.ReadInteger('Left');

//2. Последнее введенное наименование

txtName.Text:= reg.ReadString('txtName.Text');

//3. Выбранные в прошлый раз магазины

strShops:= reg.ReadString('lstShops.Selection');

shopStart:= 1;

for shopEnd:= 0 to Length(strShops) do

if strShops[shopEnd] = ',' then

begin

//Получение имени магазина и выделение его в списке

SelectShop(Copy(strShops, shopStart, shopEnd – shopStart));

shopStart:= shopEnd + 1;

end;

//4. Применение сортировки

chkSort.Checked:= reg.ReadBool('chkSort.Checked');

except

on ERegistryException do

//Игнорируем ошибки (просто не

//будут зачитаны данные из реестра,

//например, при первом запуске программы)

;

end;

reg.CloseKey();

reg.Free();

end;

//Процедура выделяет магазин с заданным названием (если он есть в списке)

procedure TForm1.SelectShop(strShopName: String);

var

i: Integer;

begin

for i:= 0 to lstShops.Count–1 do

  if lstShops.Items[i] = strShopName then

begin

lstShops.Selected[i]:= True;

Exit;

end;

end;


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

Примечание

Чтобы при первом запуске процедуры LoadFilter не появлялись сообщения об исключениях (при работе в отладчике Delphi), снимите флажок Stop on Delphi Exceptions на вкладке Language Exceptions окна Debugger Options (меню Tools ► Debugger Options).

Автозапуск программ

Так уж повелось, что, рассматривая работу с реестром, редко удается удержаться от рассказа об организации автоматического запуска приложений, минуя пресловутое меню Автозагрузка. В данной книге эта тема также будет затронута: здесь будут рассмотрены наиболее простые способы автоматического запуска не сервисных (!) программ.

В ветвях реестра HKEY_CURRENT_USER и HKEY_LOCAL_MACHINE находятся разделы SoftwareMicrosoftWindowsCurrentVersionRun иSoftwareMicrosoftWindowsCurrentVersionRunOnce. В первом (Run) сохраняются пути приложений, запускаемых при каждой загрузке Windows. В разделе же RunOnce обычно регистрируются приложения типа инсталляторов, которые запускаются при первой с момента регистрации перезагрузке Windows, но до запуска программы Проводник. При запуске приложения, зарегистрированного в ключе RunOnce, соответствующая запись из этого раздела автоматически удаляется.

От выбора ветви реестра (HKEY_LOCAL_MACHINE или HKEY_CURRENT_USER) зависит, в сеансе всех пользователей будет запускаться приложение или только определенного.

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

Пусть на форме приложения расположен переключатель с тремя положениями (рис. 7.9). Процедура, код которой приведен в листинге 7.16, устанавливает состояние переключателя в зависимости от того, в каком разделе ветви HKEY_LOCAL_MACHINE расположен параметр с именем, совпадающим с именем программы (это условность, которая нужна для работы данного примера).

Рис. 7.9. Форма после определения варианта режима запуска приложения


Листинг 7.16. Определение режима запуска приложения

procedure TForm1.GetRunMode();

var

reg: TRegistry;

begin

reg:= TRegistry.Create();

reg.RootKey:= HKEY_LOCAL_MACHINE;

//Определение способа запуска программы (по наличию значений в

//соответствующих разделах)

if reg.OpenKey('SoftwareMicrosoftWindowsCurrent VersionRun', False)

then

begin

if reg.ValueExists(Application.Title) then

begin

//Программа есть в разделе Run —

//запускается при каждой загрузке Windows

optAutoRun.Checked:= True;

reg.CloseKey();

Exit;

end;

reg.CloseKey();

end;

if reg.OpenK nKey('('SoftwareMicrosoftWindowsCurrent VersionRun Once', False)

then

begin

if reg.ValueExists(Application.Title) then

begin

//Программа есть в разделе Run Once —

//запускается один раз при старте Windows

optRunOnce.Checked:= True;

reg.CloseKey();

Exit;

end;

reg.CloseKey();

end;

//Автозапуск программы (рассматриваемым способом) не включен

optRunNone.Checked:= True;

reg.Free();

end;


Параметры запуска изменяются (в рассматриваемом приложении) при нажатии кнопки Применить (листинг 7.17).

Листинг 7.17. Применение режима запуска

procedure TForm1.cmbApplyClick(Sender: TObject);

var

reg: TRegistry;

begin

reg:= TRegistry.Create();

reg.RootKey:= HKEY_LOCAL_MACHINE;

//Отмена прошлого режима

//..удаление параметра из раздела Run

if not optAutoRun.Checked then

if reg.OpenKey('SoftwareMicrosoftWindowsCurrent VersionRun', False)

then

begin

reg.DeleteValue(Application.Title);

reg.CloseKey();

end;

//..удаление параметра из раздела Run Once

if not optRunOnce.Checked then

if reg.OpenKey('SoftwareMicrosoftWindowsCurrent VersionRunOnce',False)

then

begin

reg.DeleteValue(Application.Title);

reg.CloseKey();

end;

//Установка нового режима (создание параметра в соответствующем разделе)

if optAutoRun.Checked then

//..добавление параметра в раздел Run

if reg.OpenKey('SoftwareMicrosoftWindowsCurrent VersionRun', True)

then

begin

reg.WriteString(Application.Title, Application.ExeName);

reg.CloseKey();

end;

if optRunOnce.Checked then

//..добавление параметра в раздел RunOnce

if reg.OpenKey('SoftwareMicrosoftWindowsCurrent VersionRunOnce',True)

then

begin

reg.WriteString(Application.Title, Application.ExeName);

reg.CloseKey();

end;

//Для верности обновим показания на форме по данным из реестра

GetRunMode();

reg.Free();

end;


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

Запуск приложения из командной строки

Сразу оговорюсь, что из командной строки (например, из окна Запуск программы, открываемого командой Пуск ► Выполнить) можно запустить любое приложение: достаточно только ввести его полный или относительный (относительно рабочей папки) путь. Однако, возможно, вы замечали, что некоторые приложения можно запускать, просто указав в командной строке имя приложения, например, calc (Кулькулятор), msaccess (Microsoft Access) или winword (Microsoft Word). Далее как раз будет рассмотрен способ обеспечения возможности запуска приложения таким ускоренным способом.

Чтобы зарегистрировать приложение для быстрого запуска, можно поместить его путь в ветвь реестра SOFTWAREMicrosoftWindowsCurrentVersionApp Paths корневого раздела HKEY_CURRENT_USER или HKEY_LOCAL_MACHINE. Путь EXE-файла приложения должен быть записан в параметр (По умолчанию) подраздела, имеющего такое же имя, что и EXE-файл приложения (включая расширение).

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

Листинг 7.18. Регистрация приложения для запуска из командной строки

procedure RegisterQuickStart();

var

reg: TRegistry;

begin

reg:= TRegistry.Create();

reg.RootKey:= HKEY_LOCAL_MACHINE;

//Регистрируем программу для запуска по имени из командной строки

if reg.OpenKey(paths + ''+ Application.Title + '.exe', True) then

begin

reg.WriteString('', Application.ExeName);

reg.CloseKey();

end;

reg.Free();

end;


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

Листинг 7.19. Отмена быстрого запуска приложения

procedure UnregisterQuickStart();

var

reg: TRegistry;

begin

reg:= TRegistry.Create();

reg.RootKey:= HKEY_LOCAL_MACHINE;

//Удаляем сведения о программе из реестра

reg.DeleteKey(paths + ''+ Application.Title + '.exe');

reg.Free();

end;


В приведенных выше листингах значение константы paths равно:


const paths = 'SOFTWAREMicrosoftWindowsCurrentVersionApp Paths';

Регистрация типов файлов

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

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

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

1. Создать раздел HKEY_CLASSES_ROOT.mydoc, в параметр (По умолчанию) которого записать имя типа файла, например, TricksDelphi.DocumentSample.

2. Создать раздел HKEY_CLASSES_ROOT<имя_типа>, например, HKEY_CLASSES_ ROOTTricksDelphi.DocumentSample. Если в параметр (По умолчанию) этого раздела записать строку, то она будет отображаться в качестве описания типа файла.

3. Если нужно, чтобы для документа использовался определенный значок, необходимо создать раздел HKEY_CLASSES_ROOT<имя_типа>DefaultIcon, в параметр (По умолчанию) которого записать полный путь EXE– или DLL-файла, содержащего необходимый значок, и через запятую номер значка (см. гл. 4).

4. Наконец, для автоматического запуска приложения при выборе файла заданного типа нужно создать раздел HKEY_CLASSES_ROOT<имя_типа>ShellOpenCommand, в параметр (По умолчанию) которого записать строку вида <путь_приложения> %1 для передачи имени документа командной строке.

Описание процедуры, производящей все вышеперечисленные операции, приведено в листинге 7.20.

Листинг 7.20. Регистрация типа файла

procedure RegisterAppDocuments();

var

reg: TRegistry;

begin

reg:= TRegistry.Create();

reg.RootKey:= HKEY_CLASSES_ROOT;

//Вносим информацию о типе файлов в реестр

//..само расширение

if reg.OpenKey('.mydoc', True) then

begin

reg.WriteString('', 'TricksDelphi.DocumentSample');

reg.CloseKey();

end;

//..описание типа файла

if reg.OpenKey('TricksDelphi.DocumentSample', True) then

begin

reg.WriteString('', ' Документ TricksDelphi.DocumentSample');

reg.CloseKey();

end;

//..значок для файлов MYDOC-типа

if reg.OpenKey('TricksDelphi .Document SampleDefaultIcon', True) then

begin

reg.WriteString('', Application.ExeName + ', 1');

reg.CloseKey();

end;

//..приложение, открывающее MYDOC-документ

if reg.OpenKey('TricksDelphi .Document SampleShellOpenCommand', True)

then

begin

reg.WriteString('', Application.ExeName + '%1');

reg.CloseKey();

end;

reg.Free();

end;


Результат работы этой процедуры показан на рис. 7.10.

Рис. 7.10. Результат регистрации типа файла


Теперь при выборе в файловой оболочке MYDOC-приложение будет запускаться с путем выбранного файла (правда, в формате 8.3) в качестве аргумента командной строки. Как перевести путь из короткой формы в длинную (если это вообще надо), рассказано в подразделе «Преоразование длинных имен файлов в короткие и наоборот» раздела «Папки и пути» гл. 4 (стр. 129). Если вы не знакомы со способами получения доступа к аргументам командной строки, можете взглянуть на код, представленный в листинге 7.21 (здесь путь открываемого файла выводится в текстовое поле на форме).

Листинг 7.21. Определение имени открываемого файла

procedure TForm1.FormCreate(Sender: TObject);

begin

if ParamCount() > 0 then

begin

//Обрабатываем данные командной строки...

txtDoc.Text:= 'Имя открываемого файла: '+ ParamStr(1);

end;

end;


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

Листинг 7.22. Удаление из реестра сведений о типе файла

procedure UnregisterAppDocuments();

var

reg: TRegistry;

begin

reg:= TRegistry.Create();

reg.RootKey:= HKEY_CLASSES_ROOT;

//Удаление из реестра информации о типе файла

reg.DeleteKey('.mydoc');

reg.DeleteKey('TricksDelphi.DocumentSample');

reg.Free();

end;


Страницы книги >> Предыдущая | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | Следующая
  • 0 Оценок: 0

Правообладателям!

Это произведение, предположительно, находится в статусе 'public domain'. Если это не так и размещение материала нарушает чьи-либо права, то сообщите нам об этом.


Популярные книги за неделю


Рекомендации