Использование Delphi для написания расширений оболочки Windows
Друзья, знакомые с принципами работы операционных систем, знают, что полноценная операционная система представляет собой оболочку для облегчения работы обычных пользователей.
Используйте различные функции, предоставляемые операционной системой. Оболочка Windows (здесь имеется в виду операционная система Windows 95, Windows NT4.0 или выше) не только обеспечивает
Он не только предоставляет удобный и красивый графический интерфейс с графическим интерфейсом, но также предоставляет мощные функции расширения оболочки. Эти расширения оболочки можно увидеть во многих программах. Например, в вашем
Если в системе установлен Winzip, то при щелчке правой кнопкой мыши по папке или файлу в проводнике Windows файл Winzip появится во всплывающем меню.
сокращенное меню. Или папку FTP-сайта, которая отображается в проводнике Windows в Bullet FTP.
Windows поддерживает семь типов расширений оболочки (называемых обработчиками), а их соответствующие функции кратко описаны следующим образом:
(1) Обработчики контекстных меню: добавляйте контекстно-зависимые меню к определенным типам файловых объектов;
(2) Обработчики перетаскивания используются для поддержки передачи данных OLE, когда пользователи выполняют операции перетаскивания над определенными типами файловых объектов;
(3) Обработчики значков используются для предоставления уникального значка определенному файловому объекту, а также могут указывать значок для определенного типа файлового объекта;
(4) Обработчики листов PROperty добавляют страницы свойств к файловым объектам (то есть щелкните правой кнопкой мыши объект файла или объект папки и выберите «Свойства» во всплывающем меню).
диалоговое окно, появляющееся после элемента), страницы свойств могут совместно использоваться файловыми объектами одного типа или файловому объекту может быть присвоена уникальная страница свойств;
(5) Обработчики копирования будут вызываться системой, когда объект папки или объект принтера копируется, перемещается, удаляется или переименовывается через Windows.
Добавьте обработчики Copy-hook, чтобы разрешить или запретить определенные операции;
(6) Обработчики цели перетаскивания будут вызываться системой, когда объект перетаскивается на другой объект;
(7) Обработчики объектов данных будут вызываться системой при перетаскивании, копировании или вставке файлов.
Все расширения оболочки Windows основаны на компонентной модели COM (объектная модель компонентов), и оболочка обращается к объектам через интерфейсы.
Расширения оболочки разработаны как 32-разрядные серверные программы и предоставляют услуги операционной системе в виде динамически подключаемых библиотек. Поэтому, если вы хотите использовать Windows
Если пользовательский интерфейс расширяется, очень необходимо иметь некоторые знания по написанию COM-объектов. Из-за ограничений по объему COM не будет здесь представлен.
Согласно библиотеке Microsoft MSDN или связанным с ней справочным документам, интерфейс можно рассматривать как специальный класс, который содержит набор функций и процедур, которые можно использовать для управления объектом.
После написания расширений оболочки их необходимо зарегистрировать, чтобы они вступили в силу. Все расширения оболочки должны находиться в реестре Windows под ключом HKEY_CLASSES_ROOTCLSID.
Зарегистрируйтесь ниже. Под этим ключом вы можете найти множество ключей с именами типа {0000002F-0000-0000-C000-000000000046}. Такие ключи являются глобальными уникальными идентификаторами классов.
Руководство. Каждое расширение оболочки должно иметь глобальный уникальный идентификатор класса, именно так Windows находит обработчик расширения оболочки.
Местоположение библиотеки динамической компоновки расширения оболочки в системе записывается в подразделе InProcServer32 под идентификатором класса. Расширения оболочки, связанные с типом файла, регистрируются в
Под первичным ключом Shelex соответствующего типа. Если операционная система Windows — Windows NT, расширение оболочки также должно присутствовать в реестре.
Зарегистрируйтесь под первичным ключом HKEY_LOCAL_MACHINESoftwareMicrosoftWindowsCurrentVersionShellExtensionsApproved.
После компиляции программы DLL расширения оболочки вы можете использовать regsvr32.exe, предоставляемый самой Windows, для регистрации программы сервера DLL. Если вы используете Delphi, вы также можете
Для регистрации выберите «Зарегистрировать сервер ActiveX» в меню «Выполнить».
Давайте сначала познакомимся с более часто используемым приложением расширения оболочки: контекстно-зависимым меню, которое появляется, когда вы щелкаете правой кнопкой мыши файл или папку в Windows.
Это меню называется контекстно-зависимым меню. Чтобы динамически добавлять пункты меню в контекстно-зависимое меню, вы можете написать обработчик контекстного меню. Например, каждый
Знакомое программное обеспечение, такое как WinZip и UltraEdit, динамически добавляет пункты меню в меню, создавая обработчик контекстного меню. Если установлено в системе
WinZip, то при щелчке правой кнопкой мыши по файлу (папке) с именем Windows в его контекстно-зависимом меню появится пункт «Добавить в Windows.zip».
Обработчик контекстного меню, который будет реализован в этой статье, аналогичен контекстному меню, предоставляемому WinZip. Это добавит
Пункт меню «Операции с файлами», при нажатии на который интерфейсная программа выводит окно операций с файлами для выполнения копирования, перемещения и других операций с файлами.
Написание обработчика контекстного меню должно реализовать три интерфейса: IShellExtInit, IContextMenu и TComObjectFactory. Реализация IShellExtInit
Инициализация интерфейса, объект интерфейса IContextMenu реализует контекстное меню, а интерфейс IComObjectFactory реализует создание объекта.
Конкретная реализация программы представлена ниже. Сначала щелкните пункт «Файл | Новый» в меню Delphi, выберите DLL в окне «Новый элемент», чтобы создать файл проекта DLL.
Затем щелкните пункт меню «Файл|Новый», выберите «Единица измерения» в окне «Новый элемент», чтобы создать файл модуля, щелкните пункт меню «Файл|Новый» и выберите «Единица измерения» в окне «Новый элемент».
Выберите Форма, чтобы создать новое окно. Сохраните файл проекта как Contextmenu.dpr, Unit1 как Contextmenuhandle.pas и сохраните форму как
OpWindow.pas.
Список программ Contextmenu.dpr следующий:
контекстное меню библиотеки;
использует
КомСерв,
contextmenuhandle в «contextmenuhandle.pas»,
окно операции в 'opwindow.pas' {Form2};
экспорт
Длллжетклассобжект,
DllCanUnloadNow,
ДлРегистерСервер,
Дллунрегистерсервер;
{$R *.TLB}
{$R *.RES}
начинать
конец.
Список программ Contextmenuhandle выглядит следующим образом:
единица ContextMenuHandle;
интерфейс
использует Windows, ActiveX, ComObj, ShlObj, классы;
тип
TContextMenu = класс (TComObject, IShellExtInit, IContextMenu)
частный
FFileName: массив [0..MAX_PATH] символов;
защищенный
function IShellExtInit.Initialize = SEIInitialize // Избегаем предупреждения компилятора;
функция SEIInitialize (pidlFolder: PItemIDList; lpdobj: IDataObject;
hKeyProgID: HKEY): HResult;
функция QueryContextMenu (Меню: HMENU; indexMenu, idCmdFirst, idCmdLast,
uFlags: UINT): HResult;
функция InvokeCommand (вар lpici: TCMInvokeCommandInfo): HResult;
функция GetCommandString (idCmd, uType: UINT; pwReserved: PUINT;
pszName: LPSTR; cchMax: UINT): HResult;
конец;
константа
Class_ContextMenu: TGUID = '{19741013-C829-11D1-8233-0020AF3E97A0}';
{Глобальный уникальный идентификатор (GUID) — это 16-байтовое (128-байтовое) значение, которое однозначно идентифицирует интерфейс}
вар
СписокФайлов: TStringList;
выполнение
использует ComServ, SysUtils, ShellApi, Registry, UnitForm;
функция TContextMenu.SEIInitialize(pidlFolder: PItemIDList; lpdobj: IDataObject;
hKeyProgID: HKEY): HResult;
вар
СтгМедиум: ТСтгМедиум;
Форматетк: ТФорматетк;
FileNumber, я: целое число;
начинать
file://Если lpdobj равен Nil, этот вызов завершится неудачей
если (lpdobj = ноль), то начнем
Результат: = E_INVALIDARG;
Выход;
конец;
file:// сначала инициализирует и очищает FileList для добавления файлов
FileList:=TStringList.Create;
СписокФайлов.Очистить;
file://Инициализировать файл формата буфера обмена
с FormatEtc начните
cfFormat: = CF_HDROP;
ПТД := ноль;
дваспект: = DVASPECT_CONTENT;
Линдекс: = -1;
tymed:= TYMED_HGLOBAL;
конец;
Результат: = lpdobj.GetData(FormatEtc, StgMedium);
если Не удалось (Результат), то Выход;
file://Сначала запросите количество файлов, выбранных пользователем
FileNumber:= DragQueryFile(StgMedium.hGlobal,$FFFFFFFF,ноль,0);
file:// читает в цикле и сохраняет все выбранные пользователем файлы в FileList
для i:=0 до FileNumber-1 начните
DragQueryFile(StgMedium.hGlobal, i, FFileName, SizeOf(FFileName));
СписокФайлов.Добавить(FFИмяФайла);
Результат:= НЕТОШИБКИ;
конец;
ReleaseStgMedium(StgMedium);
конец;
функция TContextMenu.QueryContextMenu(Меню: HMENU; indexMenu, idCmdFirst,
idCmdLast, uFlags: UINT): HResult;
начинать
Результат:= 0;
if ((uFlags и $0000000F) = CMF_NORMAL) или
((uFlags и CMF_EXPLORE) <> 0), затем начните
//Добавляем пункт меню в контекстное меню, заголовок пункта меню — «Просмотр растрового файла».
InsertMenu(Menu, indexMenu, MF_STRING или MF_BYPOSITION, idCmdFirst,
PChar('операция с файлом'));
// Возвращаем количество добавленных пунктов меню
Результат:= 1;
конец;
конец;
функция TContextMenu.InvokeCommand (вар lpici: TCMInvokeCommandInfo): HResult;
вар
frmOP: TForm1;
начинать
// Сначала убедитесь, что процесс вызывается системой, а не программой
если (HiWord(Integer(lpici.lpVerb)) <> 0), то
начинать
Результат: = E_FAIL;
Выход;
конец;
// Определяем валидность переданных параметров
если (LoWord(lpici.lpVerb) <> 0), то начнем
Результат: = E_INVALIDARG;
Выход;
конец;
file://Создать окно работы с файлом
frmOP:=TForm1.Create(ноль);
file://добавляет список всех файлов в список в окне работы с файлами
frmOP.ListBox1.Items := FileList;
Результат:= НЕТОШИБКИ;
конец;
функция TContextMenu.GetCommandString(idCmd, uType: UINT; pwReserved: PUINT;
pszName: LPSTR; cchMax: UINT): HRESULT;
начинать
если (idCmd = 0), то начнем
если (uType = GCS_HELPTEXT), то
{Возвращает справочную информацию по этому пункту меню. Эта справочная информация будет отображаться при перемещении мыши.
Появляется в строке состояния при переходе к этому пункту меню. }
StrCopy(pszName, PChar('При нажатии на этот пункт меню будут выполнены операции с файлами'));
Результат:= НЕТОШИБКИ;
конец
еще
Результат: = E_INVALIDARG;
конец;
тип
TContextMenuFactory = класс (TComObjectFactory)
общественный
процедура UpdateRegistry (Регистр: логическое переопределение);
конец;
процедура TContextMenuFactory.UpdateRegistry (Регистр: логическое значение);
вар
ClassID: строка;
начинать
если зарегистрироваться, то начать
унаследованный UpdateRegistry(Регистр);
ClassID:= GUIDToString(Class_ContextMenu);
file://При регистрации файла библиотеки расширений добавьте библиотеку в реестр
CreateRegKey('*shellex', ', ');
CreateRegKey('*shellexContextMenuHandlers', ', ');
CreateRegKey('*shellexContextMenuHandlersFileOpreation', ', ClassID);
file://если операционная система Windows NT
если (Win32Platform = VER_PLATFORM_WIN32_NT), то
с TRegistry.Create сделать
пытаться
RootKey:= HKEY_LOCAL_MACHINE;
OpenKey('SOFTWAREMicrosoftWindowsCurrentVersionShell Extensions', True);
OpenKey('Одобрено', Истина);
WriteString(ClassID, 'Расширение оболочки контекстного меню');
окончательно
Бесплатно;
конец;
конец
еще начать
DeleteRegKey('*shellexContextMenuHandlersFileOpreation');
унаследованный UpdateRegistry(Регистр);
конец;
конец;
инициализация
TContextMenuFactory.Create(ComServer, TContextMenu, Class_ContextMenu,
', 'Расширение оболочки контекстного меню', ciMultiInstance,tmApartment);
конец.
Добавьте элемент управления TListBox и два элемента управления TButton в окно OpWindow. Список программ OpWindows.pas выглядит следующим образом:
окно модуля;
интерфейс
использует
Windows, сообщения, SysUtils, классы, графика, элементы управления, формы, диалоги,
ExtCtrls, StdCtrls, shlobj, шеллапи, ActiveX;
тип
ТФорм1 = класс (ТФорма)
Список1: TListBox;
Кнопка1: Кнопка T;
Кнопка2: Кнопка T;
процедура FormCreate (Отправитель: TObject);
процедура FormClose (Отправитель: TObject; вар Действие: TCloseAction);
процедура Button1Click (Отправитель: TObject);
процедура Button2Click (Отправитель: TObject);
частный
{Частные заявления}
общественный
СписокФайлов: TStringList;
{Публичные заявления}
конец;
вар
Форма1: ТФорм1;
выполнение
{$R *.DFM}
процедура TForm1.FormCreate(Отправитель: TObject);
начинать
FileList:=TStringList.Create;
Button1.Caption :='Копировать файл';
Button2.Caption :='Переместить файлы';
Селф.Шоу;
конец;
процедура TForm1.FormClose(Отправитель: TObject; var Action: TCloseAction);
начинать
СписокФайлов.Бесплатно;
конец;
процедура TForm1.Button1Click(Отправитель: TObject);
вар
путь: строка;
fsTemp:SHFILEOPSTRUCT;
я: целое число;
начинать
sPath:=InputBox('Операция с файлом','Входной путь копирования','c:windows');
если sPath<>', то начнем
fsTemp.Wnd := Self.Handle;
file://установить тип операции с файлом
fsTemp.wFunc:=FO_COPY;
file:// позволяет отменить операции
fsTemp.fFlags:=FOF_ALLOWUNDO;
для i:=0 до ListBox1.Items.Count-1 начать
file://полный путь к исходному файлу
fsTemp.pFrom := PChar(ListBox1.Items.Strings[i]);
file://путь для копирования
fsTemp.pTo := PChar(sPath);
fsTemp.lpszProgressTitle:='Копировать файл';
если SHFileOperation(fsTemp)<>0, то
ShowMessage('Не удалось скопировать файл');
конец;
конец;
конец;
процедура TForm1.Button2Click(Отправитель: TObject);
вар
путь: строка;
fsTemp:SHFILEOPSTRUCT;
я: целое число;
начинать
sPath:=InputBox('Операция с файлом','Введите путь перемещения','c:windows');
если sPath<>', то начнем
fsTemp.Wnd := Self.Handle;
fsTemp.wFunc:=FO_MOVE;
fsTemp.fFlags:=FOF_ALLOWUNDO;
для i:=0 до ListBox1.Items.Count-1 начать
fsTemp.pFrom := PChar(ListBox1.Items.Strings[i]);
fsTemp.pTo := PChar(sPath);
fsTemp.lpszProgressTitle:='Переместить файлы';
если SHFileOperation(fsTemp)<>0, то
ShowMessage('Не удалось скопировать файл');
конец;
конец;
конец;
конец.
Щелкните элемент Project | Build ContextMenu в меню, и Delphi создаст файл Contextmenu.dll. Это программа контекстно-зависимого меню.
Используйте Regsvr32.exe для регистрации программы, затем щелкните правой кнопкой мыши по любому одному или нескольким файлам в проводнике Windows, и он появится в контекстном меню.
Существует дополнительный пункт меню для операций с файлами. Нажмите на этот пункт, и имена всех выбранных вами файлов будут перечислены в списке во всплывающем окне. Вы можете выбрать кнопку копирования файла или .
Кнопка «Переместить файл» выполняет операции с файлами.