(18.02.2012 16:27)totkotoriy Wrote: А может есть у кого-нибудь готовый код для C++ на создание нового триггера? А то че-то теперь в героях ошибки полезли
PROCEDURE HookCode(P: POINTER; NewAddr: POINTER; UseCall: BOOLEAN);
VAR
HookRec: THookRec;
BEGIN
IF UseCall THEN BEGIN HookRec.Opcode:=C_OPCODE_CALL;
END // .if
ELSE BEGIN HookRec.Opcode:=C_OPCODE_JUMP;
END; // .else
HookRec.Ofs:=INTEGER(NewAddr)-INTEGER(P)-C_UNIHOOK_SIZE;
WriteAtCode(P, @HookRec, 5);
END; // .procedure HookCode
PROCEDURE HOOK_tent; ASSEMBLER; {$FRAME-}
ASM
MOV EAX, $50C7C0
CALL EAX //вызываем функцию вычисления HP-очков, которую мы затёрли своим хуком.
MOV DWORD PTR DS:[$91DA38],-1 //заносим в адрес переменной x1 значение -1 - на случай, если мы не хотим вообще ничего менять в принципе лечения
MOV [$91DA3C], EAX //заносим в адрес переменной x2 исходное значение кол-ва хит-пойнтов, для подробностей и возможных вычислений
PUSHAD //сохраняем регистры
PUSH 29500 //номер ERM-функции. Меняйте на любой доступный.
MOV EAX, $74CE30
CALL EAX //вызываем C_FUNC_ZVS_CALLFU
ADD ESP, 4
POPAD //выталкиваем регистры
CMP DWORD PTR DS:[$91DA38],-1 //проверяем, изменил ли скриптописец кол-во очков HP для лечения
JE @@Default //если не изменил - продолжить код без изменения
MOV EAX,DWORD PTR DS:[$91DA38] // заменить значение очков на значение из x1
@@Default:
PUSH $478538 //адрес возврата в процедуру
END;
BEGIN
HookCode(POINTER($478533), @HOOK_tent, C_HOOKTYPE_JUMP);
END.
Обработчик хука на ассемблере. Перенести в С++ легко, если сам хук сможешь создать. В теме " Исследование героев" раздела "Моды" есть еще более подробный комментарий, если комментария в тексте недостаточно.