Загрузка данных


import cv2
import mss
import numpy as np
import pydirectinput
import time

print("ИИ-ШТУРМОВИК С СИСТЕМОЙ ВИРТУАЛЬНОГО БАМПЕРА ЗАПУЩЕН! Жду входа в бой...")

# Твои идеальные размеры захвата экрана
monitor = {"top": 0, "left": 0, "width": 650, "height": 370}

# ИДЕАЛЬНАЯ ЦВЕТОВАЯ ПАЛИТРА ИЗ ТВОИХ СКРИНШОТОВ (HSV)
lower_green = np.array([35, 50, 50])
upper_green = np.array([85, 255, 255])

lower_blue = np.array([90, 50, 50])
upper_blue = np.array([130, 255, 255])

lower_red1 = np.array([0, 100, 100])
upper_red1 = np.array([10, 255, 255])
lower_red2 = np.array([160, 100, 100])
upper_red2 = np.array([180, 255, 255])

ATTACK_JOYSTICK_X = 570
ATTACK_JOYSTICK_Y = 240

with mss.mss() as sct:
    is_moving_forward = False
    wall_avoid_mode = False
    wall_avoid_start_time = 0
    avoid_direction = 'a'
    
    while True:
        screenshot = sct.grab(monitor)
        frame = np.array(screenshot)
        frame = cv2.cvtColor(frame, cv2.COLOR_BGRA2BGR)
        hsv = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV)
        
        # Получаем контуры ХП
        mask_g = cv2.inRange(hsv, lower_green, upper_green)
        mask_r1 = cv2.inRange(hsv, lower_red1, upper_red1)
        mask_r2 = cv2.inRange(hsv, lower_red2, upper_red2)
        mask_r = cv2.bitwise_or(mask_r1, mask_r2)
        
        contours_g, _ = cv2.findContours(mask_g, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
        contours_r, _ = cv2.findContours(mask_r, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
        
        in_battle = len(contours_g) > 0 or len(contours_r) > 0
        if not in_battle:
            if is_moving_forward:
                pydirectinput.keyUp('w')
                is_moving_forward = False
            pydirectinput.keyUp('a')
            pydirectinput.keyUp('d')
            cv2.imshow("AI Vision - Waiting for Battle", frame)
            if cv2.waitKey(1) & 0xFF == ord('q'):
                break
            continue

        me_x, me_y = None, None
        enemy_detected = False
        enemy_x, enemy_y = None, None
        
        screen_center_x = 650 // 2
        screen_center_y = 370 // 2
        closest_dist = 99999
        
        # 1. Находим себя
        for contour in contours_g:
            if cv2.contourArea(contour) > 120:
                x, y, w, h = cv2.boundingRect(contour)
                if w > h * 2.5 and w < h * 5.5:
                    dist = abs(x + w//2 - screen_center_x) + abs(y + h//2 - screen_center_y)
                    if dist < closest_dist:
                        closest_dist = dist
                        me_x, me_y = x + w//2, y + h//2

        # 2. Находим врага
        closest_enemy_dist = 99999
        for contour in contours_r:
            if cv2.contourArea(contour) > 120:
                x, y, w, h = cv2.boundingRect(contour)
                if w > h * 2.5 and w < h * 5.5:
                    enemy_detected = True
                    ex, ey = x + w//2, y + h//2
                    if me_x is not None:
                        e_dist = np.sqrt((ex - me_x)**2 + (ey - me_y)**2)
                        if e_dist < closest_enemy_dist:
                            closest_enemy_dist = e_dist
                            enemy_x, enemy_y = ex, ey

        # --- СИСТЕМА ВИРТУАЛЬНОГО БАМПЕРА СТЕН ---
        if me_x is not None and me_y is not None:
            # Сканируем маленькую зону прямо НАД головой Кольта (на 40 пикселей выше полоски ХП)
            # Если там стена/вода — в этой зоне будет много резких контуров или теней
            bumper_y_start = max(0, me_y - 50)
            bumper_y_end = max(0, me_y - 15)
            bumper_x_start = max(0, me_x - 25)
            bumper_x_end = min(650, me_x + 25)
            
            # Вырезаем зону бампера для анализа краев (Canny)
            bumper_zone = frame[bumper_y_start:bumper_y_end, bumper_x_start:bumper_x_end]
            if bumper_zone.size > 0:
                gray_bumper = cv2.cvtColor(bumper_zone, cv2.COLOR_BGR2GRAY)
                edges = cv2.Canny(gray_bumper, 50, 150)
                edge_count = np.sum(edges > 0)
                
                # Рисуем рамку бампера на экране для наглядности (Желтая — свободно, Фиолетовая — стена!)
                if edge_count > 80 and not wall_avoid_mode:
                    print("⚠️ БАМПЕР: Обнаружено препятствие (Стена/Вода)! Меняю курс!")
                    wall_avoid_mode = True
                    wall_avoid_start_time = time.time()
                    avoid_direction = 'a' if me_x > screen_center_x else 'd'
                    pydirectinput.keyUp('w')
                    is_moving_forward = False
                
                # Подсвечиваем бампер на видео
                color = (255, 0, 255) if wall_avoid_mode else (0, 255, 255)
                cv2.rectangle(frame, (bumper_x_start, bumper_y_start), (bumper_x_end, bumper_y_end), color, 2)

        # --- МАНЕВРИРОВАНИЕ И АТАКA ---
        if enemy_detected and me_x is not None:
            if wall_avoid_mode:
                if time.time() - wall_avoid_start_time < 0.5:
                    pydirectinput.keyDown(avoid_direction)
                else:
                    pydirectinput.keyUp(avoid_direction)
                    wall_avoid_mode = False
            else:
                if not is_moving_forward:
                    pydirectinput.keyDown('w')
                    is_moving_forward = True

            # КИБЕРСПОРТИВНОЕ ПРИЦЕЛИВАНИЕ
            dx = enemy_x - me_x
            dy = enemy_y - me_y
            distance = np.sqrt(dx**2 + dy**2)
            
            if distance > 0:
                aim_click_x = int(ATTACK_JOYSTICK_X + (dx / distance) * 45)
                aim_click_y = int(ATTACK_JOYSTICK_Y + (dy / distance) * 45)
                pydirectinput.moveTo(ATTACK_JOYSTICK_X, ATTACK_JOYSTICK_Y)
                pydirectinput.mouseDown()
                pydirectinput.moveTo(aim_click_x, aim_click_y)
                pydirectinput.mouseUp()
            
            pydirectinput.press('f')
            pydirectinput.press('e')
        else:
            if is_moving_forward:
                pydirectinput.keyUp('w')
                is_moving_forward = False
            pydirectinput.keyUp('a')
            pydirectinput.keyUp('d')

        cv2.imshow("AI Vision - Anti-Wall Battle Mode", frame)
        if cv2.waitKey(1) & 0xFF == ord('q'):
            pydirectinput.keyUp('w')
            pydirectinput.keyUp('a')
            pydirectinput.keyUp('d')
            break

cv2.destroyAllWindows()
print("Бот остановлен.")