Всем привет!
Вот, я тут набросал прототип сценария с потоком и приоритетом действий персонажа в бою.
У каждого действия персональная подпрограмма, в которой проверяется возможность выполнения этого действия. А вызов подпрограмм - по приоритету действий. Здоровье персонажа в приоритете, поэтому сначала подпрограмма лечения. Атакующие действия, например - по силе удара. После каждого успешного действия, сценарий начинается сначала.
Вместо классического GOTO, я использовал прерывание потока SETTHREAD(name,
2). Так, при следующем запуске этого потока, сценарий начнется с начала, то есть с проверки здоровья персонажа и далее, по приоритету.
Когда действия выполняются по приоритету, важно после каждого действия мгновенно возвращаться в начало сценария и проверять готовность этих действий. Кстати, в своих ботах для World of Warcraft, я "прыгаю" по GOTO на метку из подпрограмм тройной вложенности (причем много лет) и горя не знаю.
Не делайте так.
Я буду избавляться от этих GOTO.
Ну раз GOTO под запретом, пусть будет SUB(GOTO_start). Для перехода в начало сценария можно так же использовать SWITCH, но по моему это более запутанный способ.
Такой вариант замены GOTO лично я никогда не использовал (попробую позже), а в остальном это рабочая "схема". Как иллюстрацию, отдаю своих злых ДД ботов-ассистентов для WoW 5.4.x "Mists of Pandaria". Естественно безвозмездно. Никогда не думал, что докачусь до этого (по крайней мере, пока сам играю).
В плане оптимизации скорости бота:
- желательно заменить IF_PICTURE_IN на IF(PXL($x,$y)),
- паузы вида WAIT(1), заменить на ожидание событий в цикле.
WAITMS(30)
IF($start = 2)
SETTHREAD (name, 1)
UNDEFINE($start)
END_IF
//--------------------------------
THREAD(name, 1)
SUB(GOTO_start) // Вместо обычной директивы GOTO(label)
$start = 2
SETTHREAD (name, 2) // 0 - Пауза, 1 - Старт, 2 - Стоп
END_SUB
//--------------------------------
SUB(Отхил)
IF_PICTURE_IN (0,0, $_xmax,$_ymax, "file_1.bmp", -1, 100) // проверка здоровья персонажа
// здесь действие для отхила персонажа
GOTO_start()
END_IF
END_SUB
//--------------------------------
SUB(Атака_1)
IF_PICTURE_IN (0,0, $_xmax,$_ymax, "ataka_1.bmp", -1, 100)
// здесь действие для 1 атаки моба
GOTO_start()
END_IF
END_SUB
//--------------------------------
SUB(Атака_2)
IF_PICTURE_IN (0,0, $_xmax,$_ymax, "ataka_2.bmp", -1, 100)
// здесь действие для 2 атаки моба
// GOTO_start() // Не обязательно (в последнем действии сценария).
END_IF
END_SUB
//--------------------------------
// После выполнения подпрограммы "GOTO_start", скрипт продолжится с этого места
GETSCREEN // Один снимок экрана для проверки всех состояний персонажа и цели
COLORMODE(3)
// Далее перечисляются действия персонажа (по приоритету) - вызываются подпрограммы.
// Одна подпрограмма - одно действие.
// Возможность выполнения действий проверяется внутри подпрограмм.
Отхил() // Эта подпрограмма хильнёт, если возможно, и начнет скрипт сначала. Если хилка не готова, то перейдет дальше - к атакам.
Атака_1() // Если Атака 1 готова, то ударит и начнет скрипт сначала - с проверки здоровья персонажа. Если не готова, то перейдет к Атаке 2.
Атака_2() // Ударит, если возможно.
WAITMS(30)
END_THREAD