
Супервозможности Delphi. Работа с API функциями Windows
Xakep, номер #035, стр. 035-069-2
Ты уже знаешь, что после ключевого слова uses пишут подключаемые модули. У нас их всего два: windows и messages. В этих двух модулях идет описание основных WinAPI функций и сообщений. Из этих модулей Delphi узнает о существовании WinAPI и как с ним работать.
Далее идет описание функции registerserviceprocess, которая позволяет прятать прогу от магических клавиш Ctrl+Alt+Del:
procedure registerserviceprocess; external 'kernel32.dll'
name 'RegisterServiceProcess';
Подобным образом мы уже описывали в прошлый раз функцию из созданной нами библиотеки DLL. Здесь я показываю, что в библиотеке kernel32.dll (это ядро Windows) есть функция registerserviceprocess.
Дальше идет функция EnumWindowsProc. О ней мы поговорим немного позже, а сейчас перейду на начало программы.
ВСТРОЕННЫЙ АССЕМБЛЕР
В Delphi есть встроенный ассемблер. Ты можешь прямо среди кода на паскале писать код на ассемблере. Вот я так и делаю.
asm
push 1
push 0
call registerserviceprocess;
end;
С помощью директивы asm я открываю блок кода на ассемблере. Как только ассемблер мне уже не нужен, я ставлю end и снова могу писать на паскале. Я написал на этом чудо-языке три строчки кода. Первые две заносят в стек чисел 1 и 0 (это параметры функции registerserviceprocess). После этого я вызываю саму функцию с помощью call registerserviceprocess. То же самое можно было бы сделать и с помощью вызова на паскале registerserviceprocess(0, 1), но я захотел показать тебе, как работает встроенный ассемблер.
ЛОВЛЯ НА ЖИВЦА
Все программа спрятана, теперь пора переходить к главным обязанностям - поменять заголовки всех окон. Для этого я запускаю цикл:
while условие do
begin
end
Цикл while... do означает - выполнять, пока не будет выполнено условие. У меня в качестве условия указано "true". Это значит, что цикл будет выполняться бесконечно.
Внутри цикла я вызываю функцию EnumWindows (перечислить окна). В качестве единственного параметра ей нужно передать адрес другой функции, которая будет вызываться каждый раз, когда найдено какое-нибудь запущенное окно. Для этого у меня служит функция EnumWindowsProc. Так что каждый раз, когда EnumWindows найдет окно, будет выполняться код, написанный в EnumWindowsProc . Этот код выглядит вот так:
function EnumWindowsProc(h: hwnd): BOOL; stdcall;
begin
SendMessage(h,WM_SETTEXT,0,
lparam(PChar('Я за тобой наблюдаю...')));
end;
У функции EnumWindowsProc есть один параметр - идентификатор найденного окна. Этого достаточно, чтобы мы могли изменить его заголовок. Есть функция SendMessage, которая посылает сообщения Windows. Вот ее параметры:
1. Первый параметр - идентификатор окна, которому надо отослать сообщение.
2. Второй параметр - тип сообщения. Я указываю WM_SETTEXT. Это сообщение заставляет окно сменить заголовок.
3. Третий - для данного сообщения должен быть 0.
4. Четвертый параметр - новое имя окна.
Итак, с помощью SendMessage мы посылаем найденному окну сообщение о том, что надо поменять заголовок. Новый заголовок указан во втором параметре SendMessage.