-
Постов
2 999 -
Зарегистрирован
-
Победитель дней
129
Тип контента
Профили
Форумы
Загрузки
Блоги
Весь контент MasterGH
-
Читайте статьи и форум. Ваш вопрос это вопрос "новичка",а новичок должен учиться самостоятельно по существующим статьям, видео и т.п. Если хотите больше шансов на ответ, то нужно задавать более конкретные вопросы, предоставляя больше начальной и подробной информации. По поводу скорострельности и отдачи боюсь, если Вам ответят как это сделать Вы все равно ничего не поймете. Кстати и не каждому это под силу.
-
Исправлено мной спустя год )
-
control_setPosition() - устанавливает позицию объекта TControl или объекта, который наследует класс TControl. Файл примера: DragWindow.rar Статья: Перетаскиваемая форма на Lua.rar Код из статьи:
-
Пример, который я предложил Дарк Байту. function FormMouseDown(sender, button, x, y) ReleaseCapture() // новая функция frmHandle = wincontrol_getHandle(UDF1) // новая функция if frmHandle==nil then return WM_SYSCOMMAND = 274 SendMessageA(frmHandle,WM_SYSCOMMAND,0xF012,0) // новая функция end Надеюсь он введёт поддержку. Ну а до тех пор, проще всего сделать движение формы за мышкой по текущим и новым её координатм обрабатывая события удерживания и отпуска. -------- Я всё-таки решил тебе чуть помочь, потому что понял, что по первому способу у тебя трудности. Тем не менее тебе ещё предстоит написать dx и dy работу для того чтобы курсор мышки был там где он должен быть а не в левом верхнем углу при перетаскивании. На форме UDF1 есть картинка. Когда на картинку нажали или был клик, то ставим булевы переменные. Таймер работает по логике этих переменных. В данном коде курсор всегда будет в верхнем левом углу и только при клике на картинку. Остальное предоставляю тебе доработать самому. form_show(UDF1) isMouseDown = false; isMouseUp = false; --dx = 0 --dy = 0 function OnTimerDrag() if isMouseDown then mx,my = getMousePos() --dx = dx - mx --dy = dy - my --x, y = control_getPosition(UDF1) control_setPosition(UDF1, mx, my) end end timer1 = createTimer(UDF1) timer_setInterval(timer1, 50) timer_onTimer(timer1, OnTimerDrag) function CEImage1MouseDown(sender, button, x, y) isMouseDown = true isMouseUp = false end function FormClick(sender) isMouseDown = false isMouseUp = true end Ну и на всякий случай, таблица в формате .CT. DragWindow.rar Откроешь таблицу. Согласишься запустить Lua -скрипт. Удерживаем левую кнопку мышки на картинке и тянем куда-нибудь и видим перемещение.
-
По точнее не могу объяснить Как я писал используй первый способ.
-
Если было бы именно так просто, то я бы наверняка написал бы готовый ответ Речь идёт о Lua-Engine поддержке, а не о полноценном языке программирования под Windows. 1) Lua-engine явно не поддерживает посылку сообщений: SendMessage(Handle,WM_NCLBUTTONDOWN,HTCAPTION,0) 2) Явно не поддерживает поиск дескриптора окна. 3) Мелочь, но все же, имхо, некрасиво эмулировать HTCAPTION, когда заголовка в окне не видно. Если делаем перетаскивание, то делаем его через WM_SYSCOMMAND и SC_DRAGMOVE. Первый и второй пункт означают, что нужно изворачиваться с автоассемблером совместно с Lua-Engine. Вижу несколько способов решения с таймером/потоком или тот способ который я описал. Да, ещё один способ написать Даркб Байту чтобы ввел поддержу работу с дескрипторами форм.
-
Данную функцию нужно писать. Простой способ 1: перемещать форму за курсором когда нажата левая кнопка мышки. Это способ можно найти в Интернете задав запрос "перемещение формы за курсором" Самый красивый способ 2 это сделать инъекцию кода в процесс CE с помощью АА-скрипта на обработку любых поступающих сообщений в форму трейнера с выполнением следующего условия. Если было сообщение о нажатии левой кнопки мышкив окне трейнера, то выполнить внутри Новая память: WM_SYSCOMMAND = 0x0112; SC_DRAGMOVE = 0xF012; ReleaseCapture(); SendMessage(Handle, WM_SYSCOMMAND, SC_DRAGMOVE, 0); Возврат назад Естественно этот код нужно написать на автоассемблере и это надо сделать на Lua-Engine открыв процесс CE и на том же Lua коде использовать функцию выполнения скрипта автоассемблера. Сделав инъекцию кода можно спокойно отключиться от процесса CE. Если это автономный трейнер, то нужно делать инъекцию в процесс этого трейнера и затем отключиться от него.
-
memcpy((void*)4553935, "\x75\x12", 3); Вместо "\x75\x12" должен быть указатель на данные.
-
Как уже написали у версии CE 6.1 проблемы с кодировкой. А точнее с ANSI и UTF8. В CE 6.1 не используйте русские символы: ни в таблицах, ни в трейнерах, не в формах, не в путях каких-либо, ни в комментариях. Используйте только английский язык. Русский текст можно делать на картинках. В CE 6.2 этих проблем не будет, т.е тех о которых сообщали Дарк Байту.
-
А что сложного? В "документации" всё написано ( все функции написаны в main.lua, который лежит в папке с CE ) Предполагается, что фай музыки добавлен в ресурсы. Создана форма и на форме есть кнопка, у которой есть событие CEButton1Click musicName = 'music.xm' XMFILE=findTableFile(musicName) if (XMFILE==nil) then print('Er.: File '..musicName..' is not found!') setProperty(CEButton1, "Caption", "Er.") else xmplayer_playXM(XMFILE) setProperty(CEButton1, "Caption", "Music On") end function CEButton1Click(sender) if xmplayer_isPlaying() then xmplayer_pause() setProperty(CEButton1, "Caption", "Music Off") else xmplayer_resume() setProperty(CEButton1, "Caption", "Music On") end end
-
Не долго, если знать как. Займёт 10 -15 минут. Второй (твой способ ниже) ещё труднее Идея по описанию не плохая. Задержки могут быть как уменьшающийся счётчик. Например, от 1200 до 0. И никакого понятия не будет, сколько в мс единиц этого счётчика. Допустим за 300 мс, счётчик уменьшился с 1200 до 0. Очень много тонкостей здесь по нахождению адреса таймера или счётчика по приблизительному вычислению времени между бряками. Возможно этот способ не прокатит на большинстве игр. Это довольно муторно. Даже на CE Lua-Engine будет попроще. Вот мой пример как я искал таймер при выстреле оружия (заняло меньше 10 минут) 1) В CE Находим адрес патронов дробовика 2) Ставим бряк на запись 3) Автотрейсим (есть такая опция в CE) по 10000 инструкций, получаем дерево вызовов 4) На каждый вызов сверху вглубь ставим бряки. Если прерываемся, то этот бряк не нужен и идём вглубь к следующему. Так мы отсеем участки кода, которые срабатывают без ввода(без кликов) от пользователя. Как только прерываться перестали, то теперь ставим бряки и кликаем, но уже правой кнопкой мышки. Дело в том что мы таким образом дойдём до участка кода, который распознаёт какой-либо ввод отличный от левого клика - выстрела. Наконец нашли такой бряк на адресе, где распознаётся ввод. В глубину ещё остаётся три бряка до бряка записи патронов. 5) Теперь надо выяснить какой из оставшихся бряков реагирует только на левый клик и не реагирует когда клики идут очень быстро. Я использовал Lua-код для ведения лога в отладчике. И установил что следующий в глубь участок кода, как раз не работает при очень быстрых кликах { делать выстрелы } иначе { продолжать задерживать выстрелы }если ((таймер остановился для выстрела) и (т.п.)) Ну, а если в псевдокоде IDA, то { int v1; // esi@1 int v2; // eax@1 signed int v3; // eax@4 int v4; // eax@8 double v5; // ST10_8@13 v1 = a1; v2 = (*(int (__stdcall **)(_DWORD))(**(_DWORD **)(a1 + 40) + 488))(*(_DWORD *)(a1 + 372)); if ( v2 && (*(_DWORD *)(v2 + 32) > 0 || (*(int (__thiscall **)(int))(*(_DWORD *)(v2 + 44) + 132))(v2 + 44) == -1) && (v3 = *(_DWORD *)(v1 + 48), v3 != 2) && v3 != 3 && (v3 < 4 || v3 > 6) || (v4 = *(_DWORD *)(v1 + 48)) == 0 || v4 == 3 || v4 == 5 && (unsigned __int8)sub_104CB430() ) { sub_104C6150(*(float *)&v1, 0); // shot 2 *(_DWORD *)(v1 + 112) = 3; *(_BYTE *)(v1 + 116) = 0; } else { if ( *(_DWORD *)(v1 + 48) == 2 ) { v5 = IGSObject::GetTime(v1) - *(float *)(v1 + 52); if ( sub_104C5C10() - 0.1 < v5 ) { if ( !*(_BYTE *)(v1 + 116) ) *(_BYTE *)(v1 + 116) = 1; } } } }void __usercall sub_104CB1E0(int a1<eax>) Соответственно там где первый if,т.е. там где первый условный прыг пишем жёсткий JMP на код с комментарием "Shot2". Делаем это скриптом CE с сигнатурой кода, чтобы скрипт работал и на другой версии файла game_x86_rwdi.dll // MasterGH 2011 [ENABLE] aobscan(address,74xx83xxxxxx7Fxx8Bxxxx8Dxxxx8BxxxxxxxxxxFFxx83xxxx75xx8Bxxxx83) label(injectAddress) registersymbol(injectAddress) address: // "game_x86_rwdi.dll"+4CB1FC = 0x030DB1FC injectAddress: db E9 83 00 00 00 // jmp game_x86_rwdi.dll+4CB284 nop [DISABLE] injectAddress: db 74 30 //je game_x86_rwdi.dll+4CB22E db 83 78 20 00 // cmp dword ptr [eax+20],00 unregistersymbol(injectAddress)// Fast Shot В этом случае все задержки пропали. Дальше копать не стал, т.к. мне лень. Если патроны бесконечные, можно стрелять очень быстро нажимая на мышку без конца. Правда прицел скачет как бешеный. Бесконечные патроны делал заморозив адрес патронов дробовика на 14 патронах.
-
Версия игры (Update3); версия таблицы 1.0; +1; дата создания 22.09.2011 Описание: 1) Стрельба без задержек Таблица: DeadIslandGame.rar Дополнительная информация:
- 4 ответа
-
- 2
-
-
Эту тему я хотел написать во флудильне как простое задание для любителей и думал сам не решу до конца. На своё удивления следуя своей логики уже опытного программиста я расколол эту задачку как орех за 15 минут. Кто желает исследуем Dead Island. Цель: 1) найти место в коде в котором идёт логическое условие - если пользователь (играет) и (может стрелять) и (нажал на левую кнопку мышки), то произвести выстрел. 2) После нахождения этого условия найти функцию "Выстрела для некотрого героя" типа void Shot(pHero * objHero) 3) Написать скрипт, который делает выстрел. -------------- Решение того что успел. 1) Ищу адрес потронов для дробовика 2) Ставлю бряк на запись 3) Прерываюсь на 02E86D9C - 50 - push eax 02E86D9D - FF D2 - call edx 02E86D9F - FF 48 20 - dec [eax+20] << 02E86DA2 - 83 C0 20 - add eax,20 02E86DA5 - E8 4666C7FF - call 02AFD3F0 EAX=34289F70 EBX=199CD788 ECX=34F10F88 EDX=02D389E0 ESI=199CD788 EDI=0000000C ESP=0018F1C8 EBP=0018F2B8 EIP=02E86DA2 4) Иду по инструкции в дизассемблер Cheat Engine. И ставлю трейс на 10000 тыс инструкций. У меня он проходит меньше чем за 15 секунд. Получаю дерево прохождения кода некотром потоком процесса игры. 5) На каждом участке вхождения в дереве сверху вглубь ставлю бряк в дизассемблере на выполнение (нажимаю F5). При это совершаю нажатие на правую, а не на левую кнопку мышки. Если бряк срабатывает, то эта инструкция не та, которая нужна. В итоге я наконец нашёл учаток: game_x86_rwdi.dll+4C5F38 - 8B C7 - mov eax,edi game_x86_rwdi.dll+4C5F3A - E8 A1520000 - call game_x86_rwdi.dll+4CB1E0 game_x86_rwdi.dll+4C5F3F - 5D - pop ebp // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< game_x86_rwdi.dll+4C5F40 - 5E - pop esi game_x86_rwdi.dll+4C5F41 - 5F - pop edi Именно здесь происходит развилка между выстрелом по левой кнопке и другими действиями. Это именно то, что нужно. 6) Декомпилируем. Оказались не в огромном switch-e, а сразу после него: if ( a2 == sub_104CC9C0() && (!*(_BYTE *)(*(_DWORD *)(v4 + 40) + 4820) || sub_10435B80() != 2) ) { if ( 1.0 == a3 ) sub_104CB1E0(v4); // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< где-то внутри будет выстрел } v4 = 199CD788 - здесь указатель на что? Пока не понятно. Но он есть в регистрах (см. выше) где был бряк при выстреле. А что если вызвать функцию sub_104CB1E0(v4) новым потоком и в eax передать 199CD788 ? [ENABLE] alloc(newmem,1024) createthread(newmem) newmem: mov eax, 199CD788 call game_x86_rwdi.dll+4CB1E0 ret [DISABLE] dealloc(newmem) О, Боже я выстрел.. Черт, я даже не думал, что получится, т.к. пишу в режиме ран-тайм... Как же всё просто оказалось Участок кода, если кому надо: game_x86_rwdi.dll+4C5F2D - D8 5C 24 14 - fcomp dword ptr [esp+14] game_x86_rwdi.dll+4C5F31 - DFE0 - fnstsw ax game_x86_rwdi.dll+4C5F33 - F6 C4 44 - test ah,44 game_x86_rwdi.dll+4C5F36 - 7A 0F - jp game_x86_rwdi.dll+4C5F47 game_x86_rwdi.dll+4C5F38 - 8B C7 - mov eax,edi game_x86_rwdi.dll+4C5F3A - E8 A1520000 - call game_x86_rwdi.dll+4CB1E0 game_x86_rwdi.dll+4C5F3F - 5D - pop ebp game_x86_rwdi.dll+4C5F40 - 5E - pop esi game_x86_rwdi.dll+4C5F41 - 5F - pop edi
-
В дизайнере форм создаёшь форму. Бросаешь на неё компоненты 3 Image и 5 Label-ов. Делаешь по три иконки для первого и второго Image (это будут кнопки). Пишешь поведения смены иконок в зависимости от работы курсора: курос над картинкой, удерживание и отпускание. Для третьего Image делаешь задний фон с панелью. Если хочешь можешь делать панель отдельно. Пишешь обработчики для игры музыки/остановки и показа Info Делаешь окно с Info Делаешь главную форму нужного типа и размера. Дописываешь нужные свойства в лайблы. Пишешь ещё какие-то свои поведения для работы трейнера по горячим клавишам и поиска процесса игры. Вот и всё. Более подробно смотри учебники по Дельфи или Лазаря по работе с визуальными компонентами (VCL)
-
Меня попросили выложить старую статью. Мне она не нравится. Она запутана и в ней не всё хорошо, но для тех, кто хочет могут почитать. Насколько помню у меня получились бесконечные патроны таким способом только в Тени Чернобыля. В статье кажется речь идёт о СТАЛКЕР-е Зов припяти 1.6 К сожалению не помню точно для какой это версии игры, может быть это для Тени Чернобыля. Оформлять некогда. Вот архив ЧАСТЬ 1_Взлом патронов в СТАЛКЕР.rar
-
Оригинальные байты не (D8 62 24 20), а (D8 64 24 20). Надо было сравнить первый и последний скриншоты.
-
Попробуй так val1_off db 0xd8,0x62, 0x24, 0x20
-
keng, если Masm нужен для трейнеров, то я рекомендую вместо этого способа создания трейнеров использовать сценарии Lua в CE и AA-скрипты. Чтобы создать заготовочную форму трейнера, тебе понадобится залезть в документацию и посмотреть как это сделать. captionWindow = 'My first Lua-trainer' function OnClose(sender) closeCE() return caFree end trainerForm = createForm() form_onClose(trainerForm, OnClose) control_setCaption(trainerForm, captionWindow) form_centerScreen(trainerForm) Более подробно здесь. Я очень жду официального появления CE Lua Engine 6.2, потому что в ней (в SDK) уже исправлены многие ошибки и появились новые возможности.
-
В отладчиках обычно раскраска определённых байтов не предусмотрена. Это не отладчик это текстовый редактор. Цвет текста я делал вручную.
-
Использование getProcessIDFromProcessName(name) не разумно в цикле таймера. Эта функция перебирает все процессы сравнивая их имена и возвращает id. Этот цикл можно применить один раз, ну два или три... но не постоянно в таймере. Это ненужные расходы ресурсов процессорного времени. Чтобы ещё меньше код тормозил нужно пользоваться не getProcessIDFromProcessName("DX2Main.exe"), а другим кодом с getOpenedProcessID(). Последняя возвратит ноль если процесс не подключен. А ещё лучше использовать автоаттач процессов (код с getAutoAttachList() ) и обработку события подключения процессов onOpenProcess(processid)...
-
Сама не найдёт в этом случае. Скрипт не будет работать например на патчах для игр Метро 2033, Дисайплс Ренесанс, Дарк Сектор и др. Более подробно здесь.
-
>>Не нужно так, я же в конце смайлик поставил - значит написал не совсем серьезно, а с неким юмором Да, действительно я грубо написал. Извиняюсь. В следующий раз буду по деликатнее. Наверно, из-за того что я с Акамой пообщался в течении недели по личной переписке. Видимо "заразился" его хамством и грубостью. Мне просто хотелось уточнить, что за функции сделаны. Теперь понятно.
-
Хм...какие "функции уже работают" и что невозможное ты делаешь? Разве ты снял старфорс с игры? Я немного удивлен. Судя по статье с драйверами Страрфорса мы и не связываемся, а работаем через ринго3.... Насколько я помню были огромные статьи по распаковке других протекторов и они были гораздо и граздо длиннее. Странно что эта статья была такой короткой. И ещё у Старфорса могут быть разные функции защиты, возможно рассмотренная не была настолько сложной во взломе. Может быть решили защиту сделать хуже, чтобы игра меньше тормозила. Скорее всего путь указателей поменяется. Поменяется частично, например, поменяется первый адрес указателя и его нужно будет найти заново. Во всяком случае предугадать сложно.
-
Вообще да, файл перевода должен быть в UTF-8. Также насколько я помню фигурировали только две кодировки ANSI и UTF8. В исходниках ревизий ты можешь увидеть функции типа utf8toansi(...) и ansitoutf8(...). Последняя должна использоваться при выводе сообщений об ошибках. Я отрапартовал в форум бета версий. Посматривай за ответом, если у тебя есть доступ.
-
SER[G]ANT, ты бы этот дело скриншотом сюда выложил бы. Я отрапортую его разработчику CE как "вероятно баг", а он уже сам решит.