Доброго времени суток!
Пишу бота для игры Легенда: Наследие Драконов, столкнулся с проблемой: скрипт срабатывает 3-4 раза, а затем сообщает о переполнении массива. Такое ощущение, что совершенно не очищаются локальные переменные при повторном вызове функции. Пробовал чистить их принудительно, но как-то не выходит.
Возможно, я просто что-то делаю не так, после JS код AutoIt какой-то непривычный =))
Выше код скрипта (промежуточный), ниже - изображение, которое нужно открыть на полный экран и запустить бота. Он будет кликать по монстрам, примерно на 3-4 круге выскочит ошибка.
Ссылка на изображение для поиска: https://yadi.sk/i/kB-ps67L9iOHJg
Пишу бота для игры Легенда: Наследие Драконов, столкнулся с проблемой: скрипт срабатывает 3-4 раза, а затем сообщает о переполнении массива. Такое ощущение, что совершенно не очищаются локальные переменные при повторном вызове функции. Пробовал чистить их принудительно, но как-то не выходит.
Возможно, я просто что-то делаю не так, после JS код AutoIt какой-то непривычный =))
Код:
; 0. Проверить активность клиента игры, при необходимости запустить
; 1. Определить границы игровых окон
; - координаты поля охоты
; - кнопок с эликсирами
; - координаты полоски здоровья
; - координаты быстрых карманов + открыть быстрые карманы
; Задать координаты кнопок
; - рюкзак
; - охота
; - локация
; 2. Определить
; - управляющие цвета
; Задать
; - таймауты задержки
; - перерывов
; 3. Написать функцию поиска и сбора ресурса по цвету
; 4. Написать функцию поиска кнопки "отмена"
; 5. Написать функцию боя
; - Функция поиска монстра по цвету
; - функция проверки найденного монстра по цвету и тексту подписи, и атаки в случае успеха
; - функция боя с триггерами:
; :: Победа при уничтожении монстра (как только цвет полоски ХП монстра уйдёт в ноль)
; :: Победа при появлении всплывающего окна с надписью "Победа"
; :: Поражение при появлении надписи "Выйти из боя"
; :: Поражение при обнулении собственного ХП (и обновление страницы)
; :: Поражение при появлении всплывающего окна "Поражение"
; 6. Написать функцию перемещения по локациям с помощью компаса
; 7. Написать функцию перемещения по локациям без компаса
Dim $_huntZone[4] = [200, 250, 1720, 975], $search_colors[3] = [0xBD320D, 0x5D271A, 0x904D4D]
Dim $bot_mirnii = 0x00FF00, $bot_passivnii = 0x66FF00, $bot_passivnii_2 = 0x99FF00, $bot_spokoyii = 0xFFFF00, $bot_razdrajennii = 0xFF9900, $bot_agressivnii = 0xFF0000, $bot_agressivnii_2 = 0xFF4D00, $colors_bot_type[7] = [$bot_mirnii, $bot_passivnii, $bot_passivnii_2, $bot_spokoyii, $bot_razdrajennii, $bot_agressivnii, $bot_agressivnii_2 ]
Global $Paused, $temp[2] = [0, 0]
HotKeySet("{PAUSE}", "TogglePause")
HotKeySet('{Esc}', '_Exit')
Sleep(3000)
While 1
Local $string = "Координаты: " & @CR, $i = 0
Sleep(100)
;MouseMove(Random(0, 1920), Random(0, 768))
$search_result = searchAllPixels($_huntZone, $search_colors, 3)
; Проход по всем координатам в массиве
; While IsNumber($search_result[$i][0])
; MouseMove($search_result[$i][0], $search_result[$i][1])
; MouseClick("left", $search_result[$i][0], $search_result[$i][1], 1)
; Sleep(100)
; $i += 1
; WEnd
Local $stop_colors[2] = [$bot_mirnii, $bot_agressivnii]
$search_result = checkBotCurrent($search_result, $stop_colors, 20, 30, 15, 0, 5)
$search_result = $search_result[1]
While IsNumber($search_result[$i][0])
MouseMove($search_result[$i][0], $search_result[$i][1])
MouseClick("left", $search_result[$i][0], $search_result[$i][1], 1)
Sleep(100)
$i += 1
WEnd
; Вывод списка координат и цветов
; While $search_result[$i][0]
; $string &= $search_result[$i][0]
; $string &= ":"
; $string &= $search_result[$i][1]
; $string &= " - color: 0x"
; $string &= StringFormat("%X", $search_result[$i][2])
; $string &= @CR
;
; $i += 1
; WEnd
; MsgBox(0, "Result", $string)
; Local $bad_bots[1] = [$bot_agressivnii]
; For $i = 0 To UBound($
; Local $color = PixelGetColor($temp[0], $temp[1])
; Local $message = "It's working!" & @CR & "Coord:" & $temp[0] & ":" & $temp[1] & @CR & "Color: 0x" & StringFormat("%X", $color) & @CR & checkBotCurrent($temp[0], $temp[1], $bad_bots, 25)
; MouseMove($temp[0], $temp[1])
; MsgBox(0, "Wow!", $message)
WEnd
Func searchHuntZone()
Local $huntZoneLocal[4] = [200, 250, 1720, 975]
return $huntZoneLocal
EndFunc
; -----------------
Func checkHuntWindow()
Local $check
; Ищем фиолетовый или красный пиксель кнопок отключения ресурсов
$check = searchPixel(0, 0, @DesktopWidth, @DesktopHeight, [0xD52EDC, 0xCE0405])
If $check[0] <> -1 Then
checkSquare($check[0], $check[1], 10)
EndIf
EndFunc
; Функция проверяет координаты найденного монстра и отделяет подходящие от неподходящих, по цвету пикселей, окружающих бота. Возвращает массив, хранящий 2 массива - "хороших" и "опасных" координат
Func checkBotCurrent($data_coords, $stop_colors, $limit_x = 20, $limit_y = 20, $drift_y = 0, $drift_x = 0, $deviation = 0)
Local $good_coords[UBound($data_coords, 1) - 1][2], $good_coords_count = 0
Local $danger_coords[UBound($data_coords, 1) - 1][2], $danger_coords_count = 0
Local $dangers_count = 0
Local $all_result[2]
; Пока не закончатся координаты
For $i = 0 To UBound($data_coords, 1) - 1
; Создаём квадрат вокруг найденного пикселя, для проверки на наличие рядом стоп-цветов (к примеру, мобов другого типа). Можно также задать смещение по x & y, а также размеры квадрата
Local $check_square = getSquare($data_coords[$i][0] + $drift_x, $data_coords[$i][1] + $drift_y, $limit_x, $limit_y)
; Обнуляем счётчик "опасности" координат перед началом проверки
$dangers_count = 0
; Пока не закончатся стоп-цвета
For $j = 0 To UBound($stop_colors, 1) - 1
; Ищем пиксель заданного цвета (с погрешностью)
PixelSearch ( $check_square[0], $check_square[1], $check_square[2], $check_square[3], $stop_colors[$j], $deviation)
; Если нашли пиксель со стоп-цветом, повышаем "опасность" координат
If Not @error Then
$dangers_count += 1
EndIf
Next
; Если у координат "опасность" = 0, записываем их в "хороший" массив
If $dangers_count < 1 Then
$good_coords[$good_coords_count][0] = $data_coords[$i][0]
$good_coords[$good_coords_count][1] = $data_coords[$i][1]
$good_coords_count += 1
; Иначе записываем в "опасный" массив
Else
$danger_coords[$danger_coords_count][0] = $data_coords[$i][0]
$danger_coords[$danger_coords_count][1] = $data_coords[$i][1]
$danger_coords_count += 1
EndIf
Next
; Результаты записываем в общий массив для возврата пользователю
$all_result[0] = clearArray($good_coords)
$all_result[1] = clearArray($danger_coords)
$good_coords_count = 0
$danger_coords_count = 0
$dangers_count = 0
Return $all_result
EndFunc
Func checkBotFree($coord_x, $coord_y, $stop_colors)
EndFunc
Func checkBotType($coord_x, $coord_y, $type)
EndFunc
Func searchAllPixels($zone, $search_colors, $deviation = 15)
Local $data_coords[100][3], $result, $result_count = 0, $no_result[2] = [-1, -1]
$data_coords[0][0] = -1
$data_coords[0][1] = -1
; В цикле заполняем для каждого из допустимых цветов массив координат
For $i = 0 To UBound($search_colors, 1) - 1
; В цикле заполняем для конкретного цвета массив координат
While $zone[1] < $zone[3]
; Выполняем поиск цвета указанной зоне, с определённым допуском оттенков
$result = PixelSearch ( $zone[0], $zone[1], $zone[2], $zone[3], $search_colors[$i], $deviation)
; Если находится искомый пиксель
If Not @error Then
; Записываем его координаты в массив
$data_coords[$result_count][0] = $result[0]
$data_coords[$result_count][1] = $result[1]
$data_coords[$result_count][2] = $search_colors[$i]
; Увеличиваем счётчик кол-ва записей в массиве
$result_count += 1
; Сдвигаем зону поиска вниз
$zone[1] = $result[1] + 1
; Обнуляем массив координат
$result[0] = -1
$result[1] = -1
If $result_count > 98 Then
ReDim $data_coords[UBound($data_coords, 1) *2]
EndIf
; Если искомые пиксели кончились, заканчиваем цикл
Else
ExitLoop
EndIf
WEnd
Next
; Зачищаем переменную-счётчик, а то ощущение, что она нифига не локальная.
$result_count = 0
; Если нашлись искомые пиксели, возвращаем массив с координатами (предварительно очистив его от пустых строчек)
If $data_coords[0][0] <> -1 Then
Return clearArray($data_coords)
; Если ничего не нашлось, возвращаем False
Else
Return False
EndIf
EndFunc
Func clearArray( $arr )
Local $j = 0
; Чистим результирующий массив от мусора
While IsNumber($arr[$j][0])
$j += 1
WEnd
Local $clear_arr[$j] = $arr
Return $clear_arr
EndFunc
Func getSquare ($coord_x, $coord_y, $limit_x = 25, $limit_y = 25)
Local $coord_square[4]
$coord_square[0] = $coord_x - $limit_x
$coord_square[1] = $coord_y - $limit_y
$coord_square[2] = $coord_x + $limit_x
$coord_square[3] = $coord_y + $limit_y
Return $coord_square
EndFunc
; Проверка наличия пикселей в заданном квадрате: координаты x & y, цвета для проверки, допустимая погрешность цвета, расстояние для задания области поиска
Func checkSquare ($coord_x, $coord_y, $check_colors, $deviation, $limit)
Local $coord_square = getSquare($coord_x, $coord_y, $limit)
Return searchPixel( $coord_square , $check_colors, $deviation )
EndFunc
Func _Exit()
Local $exit
$exit = MsgBox(1, "Отключение", "Завершить работу скрипта?", 10)
If $exit == 1 Then
Exit
EndIf
EndFunc
Func TogglePause()
$Paused = Not $Paused
While $Paused
Sleep(10)
ToolTip('Скрипт приостановлен')
WEnd
ToolTip("")
EndFunc
Выше код скрипта (промежуточный), ниже - изображение, которое нужно открыть на полный экран и запустить бота. Он будет кликать по монстрам, примерно на 3-4 круге выскочит ошибка.
Ссылка на изображение для поиска: https://yadi.sk/i/kB-ps67L9iOHJg