import yaml
import cv2
import numpy as np
import time
import os
from PIL import ImageGrab
# Oletetaan, ettC$ meillC$ on aiemmin rakentamasi master_parser moduulina
# import master_parser
class RoutineEngine:
def __init__(self, yaml_path):
with open(yaml_path, 'r', encoding='utf-8') as file:
self.routine = yaml.safe_load(file)
print(f"[*] Ladattiin rutiini: {self.routine['routine_name']}")
def execute(self):
for step in self.routine['steps']:
print(f"
[*] Suoritetaan askel {step['step']}: {step['description']}")
success = self.execute_step(step)
if not success:
print(f"[-] FATAL: Askel {step['step']} epC$onnistui kaikkien
valitsimien jC$lkeen.")
return False
print("
[+] Rutiini suoritettu onnistuneesti!")
return True
def execute_step(self, step):
# Otetaan tuore ruutukaappaus askelta varten
pil_img = ImageGrab.grab()
cv_img = cv2.cvtColor(np.array(pil_img), cv2.COLOR_RGB2BGR)
for selector in step['selectors']:
print(f" -> YritetC$C$n valitsinta: {selector['type']}")
if selector['type'] == 'template_match':
coords = self.run_template_match(cv_img, selector)
if coords:
self.perform_click(coords)
return True
elif selector['type'] == 'semantic_anchor':
coords, crop_img = self.run_semantic_anchor(cv_img, selector)
if coords:
self.perform_click(coords)
# SELF-HEALING: Jos template_match epC$onnistui mutta
semanttinen onnistui,
# pC$ivitetC$C$n template-kuva tulevaisuutta varten!
if selector.get('auto_heal', False):
self.heal_template(crop_img, step)
return True
elif selector['type'] == 'escalation':
coords = self.run_frontier_ai(selector)
if coords:
self.perform_click(coords)
return True
return False
def run_template_match(self, cv_img, selector):
template_path = selector['file']
if not os.path.exists(template_path):
print(f" [!] Templatea ei lC6ydy polusta: {template_path}")
return None
template = cv2.imread(template_path)
result = cv2.matchTemplate(cv_img, template, cv2.TM_CCOEFF_NORMED)
min_val, max_val, min_loc, max_loc = cv2.minMaxLoc(result)
if max_val >= selector['threshold']:
print(f" [+] Template Match onnistui! (Varmuus:
{max_val:.2f})")
h, w = template.shape[:2]
center_x = max_loc[0] + w // 2
center_y = max_loc[1] + h // 2
return (center_x, center_y)
print(f" [-] Template Match epC$onnistui (Varmuus: {max_val:.2f} <
{selector['threshold']})")
return None
def run_semantic_anchor(self, cv_img, selector):
print(f" [*] Ajetaan Layout Parser ja CLIP...")
# TC$ssC$ kutsuttaisiin master_parser.py:n logiikkaa:
# ast_nodes = master_parser.generate_ast(cv_img)
# enriched_nodes = master_parser.enrich_icons(ast_nodes)
# Simuloitu AST-haku aiemman tulosteesi pohjalta:
anchor_text = selector['anchor_text'].lower() # "kirjoita viesti"
target_icon = selector['target_icon'] # "paperclip icon"
# Esimerkki: Koodi lC6ytC$C$ AST:sta solmun Frame_2_Main_n85 (Kirjoita
viesti) koordinaatista Y:993
# Se etsii kaikki ikonit, joiden Y on vC$lillC$ 943 - 1043.
# Se lC6ytC$C$ Frame_2_Main_n86:n (paperclip 99%)
simulated_target_found = True
if simulated_target_found:
print(f" [+] Semanttinen haku lC6ysi ankkurin '{anchor_text}'
vierestC$ kohteen '{target_icon}'")
# Palautetaan koordinaatit ja rajattu kuva ikonista self-healingia
varten
icon_crop = cv_img[975:1005, 600:630] # Kuvitteellinen crop
return (615, 990), icon_crop
return None, None
def run_frontier_ai(self, selector):
print(f" [!] Eskaloidaan raskaalle kielimallille...")
print(f" [!] Prompt: {selector['prompt']}")
# LC$hetetC$C$n AST-MD Llama3:lle tai OpenAI:lle
# ...
return None
def heal_template(self, crop_img, step):
""" PC$ivittC$C$ rikkoutuneen template-kuvan automaattisesti uudella.
"""
# EtsitC$C$n ensimmC$inen template_match -sC$C$ntC6 tC$stC$ askeleesta
for selector in step['selectors']:
if selector['type'] == 'template_match':
template_path = selector['file']
os.makedirs(os.path.dirname(template_path), exist_ok=True)
cv2.imwrite(template_path, crop_img)
print(f" [+] SELF-HEALING: PC$ivitettiin pikselitemplate
{template_path} tulevaisuutta varten!")
break
def perform_click(self, coords):
x, y = coords
print(f" [ACTION] LC$hetetC$C$n X11-klikkaus koordinaatteihin
X:{x}, Y:{y}")
# TC$ssC$ kutsutaan xdotool tai X11-Vision-API (port 7711)
# requests.post("http://localhost:7711/click", json={"x": x, "y": y})
if __name__ == "__main__":
engine = RoutineEngine("whatsapp_routine.yaml")
engine.execute()