Решил вот поделиться с сообществом функциями управления игровым автопилотом.
Он, к сожалению, не настолько хорош как в JD или FW, но тем не менее мне нравится его использовать вместо стандартной функции движения.
Это - единственная точка входа для управления всем, что связано с автопилотом в игре.
Управление осуществляется передачей ей массива параметров :
Вот так, для того, чтобы начать движение к точке с координатами (x, y) :
procedure AutoRouteStart(x, y : integer);
var
buf : array[0..6] of integer;
begin
buf[0] := 330;
buf[1] := 0;
buf[2] := 0;
buf[3] := 0; // Команда на взлёт
buf[4] := x;
buf[5] := y;
buf[6] := 0;
InjectFunc(@AutoRouteCall, @buf, SizeOf(buf));
end;
Вот так, чтобы начать плавный подъём к указанной высоте :
procedure AutoRouteAltitude(z : integer);
var
buf : array[0..6] of integer;
begin
buf[0] := 330;
buf[1] := 0;
buf[2] := 0;
buf[3] := 1; // Команда сменить высоту
buf[4] := z;
buf[5] := 0; // Хз что, но может быть 0 или 1
buf[6] := 0;
InjectFunc(@AutoRouteCall, @buf, SizeOf(buf));
end;
И вот так, чтобы прекратить движение :
procedure AutoRouteStop();
var
buf : array[0..6] of integer;
begin
buf[0] := 330;
buf[1] := 0;
buf[2] := 0;
buf[3] := 2; // Команда стоп
buf[4] := 0; buf[5] := 0; buf[6] := 0;
InjectFunc(@AutoRouteCall, @buf, SizeOf(buf));
end;
Использовать это можно вот так :
AutoRouteStart(1350, 345);
AutoRouteAltitude(75);
Комментируем, задаём вопросы, ставим спасибы...
Lermontov
28.04.2012, 18:41
Куда "вставлять" эту функцию? В смысле перед чем или после чего?
procedure AutoRouteCall(cmd : Pointer); stdcall;
var
addr: Pointer;
begin
addr := Pointer(AutoRouteAddr);
asm
pushad
mov eax, dword ptr [PW_BASE_ADDRESS]
mov eax, dword ptr [eax + PW_DYNAMIC_BASE_OFFSET]
mov ecx, dword ptr [eax + PW_ROLE_BASE_OFFSET]
push cmd
call addr
popad
end;
end;
x3max
28.04.2012, 21:46
Куда "вставлять" эту функцию? В смысле перед чем или после чего?
повнимательнее на строку:
InjectFunc(@AutoRouteCall, @buf, SizeOf(buf));
Lermontov
28.04.2012, 22:17
повнимательнее на строку:
InjectFunc(@AutoRouteCall, @buf, SizeOf(buf));
procedure AutoPath(realcoord_X,realcoord_Y,realcoord_Z:singl e);
begin
aParams.Param1:=round(realcoord_X);
aParams.Param2:=round(realcoord_Y);
aParams.Param3:=round(realcoord_Z); // высота полета
InjectFunc(aHandle,@AutoPathCall,@aParams,SizeOf(a Params));
end;
Молодец что поделился.
vogel
29.04.2012, 14:05
На этой строчке и выбивает ошибку :cry:
Вот она, вотонаотонааа ([Ссылки могут видеть только зарегистрированные и активированные пользователи]) процедура инжекта моей мечты.
samosi
30.04.2012, 14:44
хм... После инжекта он хрен пойми куда летит... Почему так?
vogel
02.05.2012, 00:18
Он летит туда, куда посылаешь. Ровно в указанные координаты.
samosi
02.05.2012, 11:52
хм не могли бы вы дать мне код? Так как у меня он летит всегда в правый верхний угл за картой.
vogel
02.05.2012, 16:24
Просьба не путать - куда он летит и куда показывает пунктирная линия.
Летит он куда послал из функции AutoRouteStart(х. у);
А пунктирную линию рисует либо к предыдущей точке, куда ты летел вручную либо в правый верхний угол.
За корректную отрисовку отвечает другая (хз какая) функция - я её пока не нашёл.
samosi
02.05.2012, 17:01
Спс все пашет. Но линию надо доделать.
P.S. Dinmaite твоя функу почему то не пашет...(Офсеты были поменяны.)
BritishColonist
02.05.2012, 17:39
samosi, он привёл старый пример со старыми оффсетами.
ThreadAddr, ParamAddr: Pointer;
begin
if ProcessId<>0 then
begin
// ---- Выделим место в памяти процесса и запишем туда нашу функцию
ThreadAddr := VirtualAllocEx(ProcessId, nil, 256, MEM_COMMIT, PAGE_READWRITE);
WriteProcessMemory(ProcessId, ThreadAddr, Func, 256, lpNumberOfBytes);
// ---- Также запишем параметры к ней
ParamAddr := VirtualAllocEx(ProcessId, nil, aParamsSize, MEM_COMMIT, PAGE_READWRITE);
WriteProcessMemory(ProcessId, ParamAddr, aParams, aParamsSize, lpNumberOfBytes);
// ---- Создадим поток, в котором это всё будет выполняться
hThread := CreateRemoteThread(ProcessId, nil, 0, ThreadAddr, ParamAddr, 0, lpNumberOfBytes);
// ---- Ожидаем, пока функция отработает
WaitForSingleObject(hThread, INFINITE);
procedure AutoRouteStart(x, y : integer);
var
buf : array[0..6] of integer;
begin
buf[0] := 330;
buf[1] := 0;
buf[2] := 0;
buf[3] := 0; // Команда на взлёт
buf[4] := x;
buf[5] := y;
buf[6] := 0;
InjectFunc(@AutoRouteCall, @buf, SizeOf(buf));
end;
procedure TForm1.Button2Click(Sender: TObject);
begin
AutoRouteStart(1350, 345);
end;
Что не так в моем бреде?/kidding
vogel
07.05.2012, 00:33
А что не работает-то ?
Lermontov
13.05.2012, 20:29
Как заставить программу лететь по координатам указанных в, допустим, Edit1 и Edit2?
vogel
13.05.2012, 20:41
допустим, считать эти координаты из полей Text контролозв Edit1 и Edit2.
перевести их из строк в цифры, допустим StrToInt
и вызвать AutoRouteStart(x, y);
Lermontov
13.05.2012, 20:45
допустим, считать эти координаты из полей Text контролозв Edit1 и Edit2.
перевести их из строк в цифры, допустим StrToInt
и вызвать AutoRouteStart(x, y);
Можно пример, не могу понять....
dwa83
14.05.2012, 17:12
Можно пример, не могу понять....
int x=StrToInt(Form1->Edit1->Text);
int y=StrToInt(Form1->Edit2->Text);
AutoRouteStart(x, y);
[c++]
IntToStr - преобразует число в строку
FloatToStr - преобразует дробное чесло в строку
StrToFloat, StrToInt - соответственно обратное действие.
Lermontov
14.05.2012, 17:38
int x=StrToInt(Form1->Edit1->Text);
int y=StrToInt(Form1->Edit2->Text);
AutoRouteStart(x, y);
[c++]
IntToStr - преобразует число в строку
FloatToStr - преобразует дробное чесло в строку
StrToFloat, StrToInt - соответственно обратное действие.
Спасибо сам разобрался )
procedure TForm1.Button1Click(Sender: TObject);
var A: Integer;
begin
A:=StrToInt(Edit1.Text);
end;
Choochoo
07.06.2012, 08:46
ProcessId:Integer;
hProcess:Integer;
Что не так в моем бреде?/kidding
Почему Integer? нужен DWORD или Cardinal
A:=StrToInt(Edit1.Text);
Не забудте что кординаты которые надо указывать отличаются от тех которые мы видим на карте.
Прошу прощения! Какие оффсеты в новом обновлении, интересует AutoRouteAddr PW_DYNAMIC_BASE_OFFSET PW_ROLE_BASE_OFFSET. Заранее спасибо!
АпАпАпчих
30.10.2012, 12:05
Я вот давным давно писал бота, правда по старым методам банального нажатия клавиш и используя обычные чтение и запись в памяти игры, инжектами функциями не страдал, но вот хочется уже догнать прогресс)) Хочу сделать возвращение персонажа на определенную точку, если он далеко выбегает.. В общем хотелось бы задать пару вопросов по этому поводу:
1. Координаты которые указываются в данной функции, как говорилось выше, не совпадают с координатами карты мира. А какие совпадают? что считывать?
2. Что хранится по этому AutoRouteAddr = $00478ED0; адресу?
3. Есть ли еще какие-нибудь способы перемещения персонажа? (если есть , просто на словах объяснить, это так, для общего развития)
Надеюсь на вашу помощь, а то надоело видеть как чар выбегает хрен пойми куда и застревает в камнях или вообще агрится на мобов выше себя на 30 уровней)
Jok3r666
28.12.2012, 06:22
buf[0] := 330;
Почему именно 330? за что отвечает? и как было определенно что 330?
vogel
28.12.2012, 15:59
Почему 220 - я не знаю. Знают, очевидно, китайские разработчики.
Определено было в отладчике.