Всем доброго времени суток и отличного настроения! Начинаю с маленького вводного курса по написанию скриптов в Delphi. Если материал будет интересен, постараюсь данную тему не забрасывать и не откладывать в долгий ящик. Почему я выбрал язык Delphi? Ответ очевиден: для начинающего программиста, зачастую этот язык легче усваивается, чем его собратья, такие как C, C++, .NET, CSharp, VB и пр. Синтаксис этого языка настолько прост, что на нем легко как писать, так и читать исходный код. А как мы знаем учиться проще на чужих примерах. По программированию на сях в сети есть масса примеров, а вот Delphi, как всегда остался в стороне. Цель данной статьи, как раз нацелена на восполнение пробелов в данной теме. Кого данный язык не устраивает, дальше могут не читать, все остальные, как говорится: "welcome". Данный материал рассчитан на публику, которая владеет минимальными азами программирования на языке Object pascal или Dephi.
Итак, что нам необходимо:
Скачиваем и распаковываем архив с моим фреймворком в любую папку, например ..projects\DelphiHookV.
ScriptHook SDK от Alexander Blade нам понадобится для просмотра нативных функций и соответствующих им хеш кодам, но об этом позднее.
Запускаем студию, открываем проект: File => Open..
Выбираем Template.dpr, нажимаем открыть
Откроется проект. "library Template;" можно заменить на свое название, например "library MyScript", не забываем сохранить. А теперь очень важный момент! Нужно сообщить компилятору, что собирать проект мы будем под x64 архитектуру. Для этого в Project Manager выбираем Target Platform (Win32) и клацаем на нем правой клавишей мыши, нажимаем добавить.
Должно получиться так:
Подготовительные работа закончена, открываем Main.pas (можно открыть, кликнув по ссылке Main в секции Uses, комбинация CTRL + левая кнопка мыши).
В Main.pas содержатся 3 основные процедуры ScriptInit, ScriptFree, ScriptMain.
- ScriptInit - выполняется любой код инициализации до входа в главный цикл (может оставаться пустой);
- ScriptFree - выполняется любой код после завершения главного цикла (может оставаться пустой);
- ScriptMain - выполняется основной код скрипта.
В образовательных целях напишем скрипт, который позволит помигать указателями поворотов на любом транспортном средстве и сделаем синхронизацию игрового времени с текущим временем на компьютере.
Для этого инициализируем несколько переменных и структур, добавим одну функцию, а в теле процедуры ScriptMain напишем не хитрый код, см. пример:
...
implementation
var
SystemTime : TSystemTime; // структура системного времени (windows.pas)
PlayerPed : LongInt; // ID игрового персонажа
Vehicle : LongInt; ID используемого транспортного средства
Blink : TBlinker; // структура с описанием наших огней (левый, правый, оба)
Blinker : array [TBlinker] of Boolean; // для информации о состоянии огней
...
procedure SwitchBlink(const Value: TBlinker);
begin
if Blink <> Value then // если устанавливаемое значение отличается от текущего, обнулим структуру
FillChar(Blinker, SizeOf(Blinker), 0);
Blink := Value; // запишем значение, какой фонарь переключаем
Blinker[Value] := not Blinker[Value]; // переключим
Vehicle := GET_VEHICLE_PED_IS_USING(PlayerPed);
SET_VEHICLE_INDICATOR_LIGHTS(Vehicle, 1, BLINKER_LEFT[Blinker[Value], Value]); // левый
SET_VEHICLE_INDICATOR_LIGHTS(Vehicle, 0, BLINKER_RIGHT[Blinker[Value], Value]); // правый
end;
procedure ScriptMain;
begin
// enter main loop
while true do
begin
PlayerPed := PLAYER_PED_ID();
// поверяем, если наш игрок в машине
if (IS_PED_IN_ANY_VEHICLE(PlayerPed, False)) then
begin
// Включаем левый
if IsKeyJustUp(74) then // нажата и отпущена " J"
SwitchBlink(bLeft);
// Включаем правый
if IsKeyJustUp(75) then // нажата и отпущена "K"
SwitchBlink(bRight);
// Аварийка
if IsKeyJustUp(VK_F10) then
SwitchBlink(bAll);
end;
// Синхронизация часов с временем на компьютере :)
if IsKeyJustUp(VK_F12) then // F12
begin
GetLocalTime(SystemTime);
SET_CLOCK_TIME(SystemTime.wHour, SystemTime.wMinute, SystemTime.wSecond);
PLAY_SOUND_FRONTEND(0, 'NAV_UP_DOWN', 'HUD_FRONTEND_DEFAULT_SOUNDSET', True);
end;
ScriptWait(0);
end;
end;
end.
Здесь используются вспомогательные нативные функции, которые описаны в Scripting.pas:
- SET_CLOCK_TIME(Hour, Min, Sec: Word): DWORD; // установка игрового времени (часов)
- PLAY_SOUND_FRONTEND(p0, 'название звука', 'группа в которой состоит звук', Param); // проигрыш звука, если Param = True, то проигрываем один раз
- PLAYER_PED_ID(); // получить ID текущего игрового персонажа
- GET_VEHICLE_PED_IS_USING(PlayerPed); // получить ID транспортного средства
- SET_VEHICLE_INDICATOR_LIGHTS(Vehicle, p0, p1); // включить\выключить указатель поворота, где Vehicle - ID транспортного средства; p0 = 0 - правый поворот, p0 = 1 - левый поворот; p1 = true/false - включено/выключено
Вот и все. Сохраняем проект и нажимаем CTRL + F9. В каталоге с файлами проекта, должен получится файл Template.asi. Копируем получившийся плагин в папку с игрой, не забыв туда же скопировать ScriptHookV.dll и Dsound.dll. Запускаем и игру, выбираем одиночный режим. В игре жмем F12 и смотрим результат. Садимся в машину, нажимаем J, K, F10 смотрим результат.
Поздравляю, вы написали первый скрипт для GTA V в Delphi.
Несколько слов о других функциях. Все функции описаны в файлах Scripting, ScriptingEnum. Я перевел лишь малую часть из оригинального SDK. Описание остальных функции можно найти в оригинальном ScriptHook SDK. Обсуждение материала на форуме здесь. Что-то новое, можно попробовать найти на моем сайте. Гладкого кода и хороших модификаций.
|