Python da yapılan bir işlemi tekrarlatmak için ne yapmalıyım

Arkadaslar merhaba… Ekran kaydetme işleminden sonra, yapılan kaydetme işlemini benim belirlediğim sayı üzerine tekrarlanmasını nasıl belirleyebilirim. Örneğin; Bilgisayarımda fare ve mouse kaydetme işlemi başlattım. Kayıt işlemi bittikten sonra, program benim yerime işlemleri aynı sekilde yapacak. Kayıt tekrarını durdurmak istediğimde, kod içinde belirtilen tuşa basıldıgında, tekrarlamayi durdurmali. Bilen arkadaşlar kodu düzenleyip yanıtlarsa sevinirim.

import pyautogui
import json
from time import sleep, time
import pyperclip

events = None

SCROLL_SENSITIVE = 110

CHANGE_LETTERS = {
    'alt_l': 'altleft',
    'alt_r': 'altright',
    'alt_gr': 'altright',
    'ctrl_l': 'ctrlleft',
    'ctrl_r': 'ctrlright',
    'shift_l': 'shiftleft',
    'shift_r': 'shiftright',
    'page_down': 'pagedown',
    'page_up': 'pageup',
    'caps_lock': 'capslock',
    'media_volume_down': 'volumedown',
    'media_volume_up': 'volumeup',
    'print_screen': 'printscreen',
    'num_lock': 'numlock',
    'scroll_lock': 'scrolllock'
}

UTF_CHARACTERS = ['ç','ı', 'ö', 'ş', 'ğ', 'ü', '@', 'İ']

def ConvertToProperKeys(key):

    properKey = key.replace('Key.', '')

    if properKey in CHANGE_LETTERS.keys():
        return CHANGE_LETTERS[properKey]
    elif properKey in UTF_CHARACTERS:
        pyperclip.copy(properKey)
        pyautogui.hotkey('ctrl', 'v')
        return ''

    return properKey




def load_json():
    global events
    with open('events.json', 'r') as event:
        events = json.load(event)

def play():
    global SCROLL_SENSITIVE
    for x, y in enumerate(events[1:]):
        p = y['time'] -0.1
        sleep(p if p > 0 else 0)
        if y['action'] == 0:
            pyautogui.keyDown(ConvertToProperKeys(y['key']))
        elif y['action'] == 1:
            pyautogui.keyUp(ConvertToProperKeys(y['key']))
        elif y['action'] == 2:
            pyautogui.moveTo(x = y['coordinate'][0], y = y['coordinate'][1])
        elif y['action'] == 3:
            pyautogui.click(x = y['coordinate'][0], y = y['coordinate'][1])
        elif y['action'] == 4:
            pyautogui.scroll(clicks=(SCROLL_SENSITIVE if y['direction'] == 'up' else -SCROLL_SENSITIVE), x = y['coordinate'][0], y = y['coordinate'][1])

def run():
    load_json()
    print('Oynatma 5 saniye sonra başlayacak..')
    sleep(5)
    play()
    pyautogui.keyUp('esc')
if __name__ == '__main__':
    run()

ekran kaydetme dediğin print screen tuşu mu? kodu çalıştırayım dedim de event.json olmadığı için çalışmadı.

Hayir, Yani ben bilgisayarda bir işlem yaparken, klavye ve mouse de yaptıgım tüm herşeyi kaydedecek. Daha sonra bu program aracılıgıyla yaptıgım işlemleri kendisi tekrar edecek. Bu tekrar etmeyi ben durdurmadigim sürece devam edecek.

tamam anladım şimdi ama pyautogui prosu olmadığım içim kod tam ne yapıyo anlayamadım. kütüphaneyi öğrenmem lazım. o yüzden çalıştırıp bi bakayım dedim. kodun çalışır halini atabilir misin?

şuan bu kodla bir işlem yapamayız, mouse ve ekranın kaydı olması gerekir. ekran kaydettiğimizde, kaydedilen işlemi event.jason dosyasına atiyor. suan paylastıgım kod’ta, event.json dosyası içindeki hareketleri alip, benim yaptıgım işlemi tekrar ediyor. ama sadece 1 defa yapiyor. ben bunu durdurmadigim sürece döngüye sokmaya calisiyorum.

program tam olarak nerede bitiyor :smiley:

from pynput import mouse, keyboard
from time import time, sleep
import json

mouse_listener = None
start_time = None
last_coordinate = [0, 0]
# MAUS HASSASİYETİ -- (HASSASİYET ARTTIKÇA DAHA YAVAŞ ÇALIŞIR).
THRESHOLD = 200
upToNow = 0
events = []


def save_json():
    with open('events.json', 'w') as event:
        json.dump(events, event, indent=4)


# For Keyboard --
# from pynput doc.
def on_press(key):
    # current_time = time()
    try:
        save_event(current_time=round(time(), 2), action=0, key=key.char)
        print('alphanumeric key {0} pressed'.format(
            key.char))
    except AttributeError:
        save_event(current_time=round(time(), 2), action=0, key=str(key))
        print('special key {0} pressed'.format(
            key))


# from pynput doc.
def on_release(key):
    try:
        print('{0} released'.format(
            key))
        if key == keyboard.Key.esc:
            print(time() - start_time)
            # returning False stops the keyboard listener, using stop function to stop mouse listener
            mouse_listener.stop()
            save_json()
            print('Fare ve klavye kaydı durduruldu..')
            return False
        save_event(current_time=round(time(), 2), action=1, key=key.char)
    except:
        save_event(current_time=round(time(), 2), action=1, key=str(key))


# For Keyboard --

# For Mouse --
def on_move(x, y):
    save_event(current_time=round(time(), 2), action=2, coordinate=[x, y])
    print('Pointer moved to {0}'.format(
        (x, y)))


def on_click(x, y, button, pressed):
    if pressed:
        save_event(current_time=round(time(), 2), action=3, coordinate=[x, y])
    print('{0} at {1}'.format(
        'Pressed' if pressed else 'Released',
        (x, y)))


def on_scroll(x, y, dx, dy):
    save_event(current_time=round(time(), 2), action=4, coordinate=[x, y], direction=('down' if dy < 0 else 'up'))
    print('Scrolled {0} at {1}'.format(
        'down' if dy < 0 else 'up',
        (x, y)))


# For Mouse --

class ActionTypes():
    KEYPRESS = 0
    KEYRELEASE = 1
    MOUSEMOVE = 2
    MOUSECLICK = 3
    MOUSESCROLL = 4


# 0 --> keypress
# 1 --> keyrelease
# 2 --> mousemove
# 3 --> mouseclick
# 4 --> mousescroll
def save_event(current_time, action, key='', coordinate=[], direction='up'):
    global upToNow
    elapsed_time = current_time - start_time
    theduration = round(elapsed_time - upToNow, 2)
    if action == ActionTypes.KEYPRESS:
        info = {
            'time': theduration,
            'action': ActionTypes.KEYPRESS,
            'key': key
        }
    elif action == ActionTypes.KEYRELEASE:
        info = {
            'time': theduration,
            'action': ActionTypes.KEYRELEASE,
            'key': key
        }
    elif action == ActionTypes.MOUSEMOVE:
        global last_coordinate
        if abs(coordinate[0] - last_coordinate[0]) > THRESHOLD or abs(coordinate[1] - last_coordinate[1]) > THRESHOLD:
            info = {
                'time': 0,
                'action': ActionTypes.MOUSEMOVE,
                'coordinate': coordinate
            }
            last_coordinate = coordinate
            # mouse move için ayrı bir append yazdık çünkü her farklı koordinatı kaydetmek yerine
            # sadece bir öncekiyle 200 piksellik fark olan hareketleri kaydedeceğiz ve kaydettikten sonra
            # koşul sonrası append 'e de düşmemesi için return ediyorum.
            events.append(info)
        return
    elif action == ActionTypes.MOUSECLICK:
        info = {
            'time': theduration,
            'action': ActionTypes.MOUSECLICK,
            'coordinate': coordinate
        }
    elif action == ActionTypes.MOUSESCROLL:
        info = {
            'time': theduration,
            'action': ActionTypes.MOUSESCROLL,
            'coordinate': coordinate,
            'direction': direction
        }
    upToNow = elapsed_time
    events.append(info)


def settingUpMouseSensitive():
    global THRESHOLD
    print("Fare hassasiyeti(piksel) başlangıç degeri 200'dür.")
    while True:
        print('Fare Hassasiyeti değerini değiştirmek için Y harfine basınız. N harfine bastiginiz takdirde, başlangıc değeri baz alınacaktır. Kaydetmeyi durdurmak için klavyenizden ESC tuşuna basınız.')
        response = input('Y/N').lower()
        if response == 'y':
            try:
                sensitive = int(input('0-300 Arasinda Piksel Deger giriniz(mousenin hassasiyeti) (0-300):'))
                if 0 <= sensitive <= 300:
                    THRESHOLD = sensitive
                    print(f'Hassasiyet Değiştirildi. ({sensitive})')
                    break
                else:
                    print('Lütfen uygun değeri girin.')
            except:
                print('Lütfen uygun değeri girin.')
        elif response == 'n':
            print(f'Hassasiyet is {THRESHOLD}')
            break


def run():
    global start_time
    settingUpMouseSensitive()
    input('Kaydetmeye başlamak için her hangi bir tuşa basınız.')
    for x in range(4, -1, -1):
        print(x + 1)
        sleep(1)
    print('Kayıt başladı...')
    start_time = round(time(), 2)
    print(start_time)

    events.append({'time': 0, 'action': 'Recording Started'})
    global mouse_listener

    # Collect events until released
    keyboard_listener = keyboard.Listener(
        on_press=on_press,
        on_release=on_release)

    # Collect events until released
    mouse_listener = mouse.Listener(
        on_move=on_move,
        on_click=on_click,
        on_scroll=on_scroll)

    keyboard_listener.start()
    mouse_listener.start()

    keyboard_listener.join()
    mouse_listener.join()

    print(events)


if __name__ == '__main__':
    run()

hocam şöyle anlatayım. son attıgım kodlarda mouse ve fare kayıt işlemi yapiyor. en üstteki kodlarda bu kayıt işlemini oynatmaya yarıyor. ben bu 2 kodu exe’ye döktüm. Oluşturdugumuz python proje dosyasındaki dist klasörü içine geliyor exe’ler. kayıt baslat programına tıkladıgımızda mouse ve fare hareketlerini kaydediyor. durdurdugumuz da dist klasörü içine event.json dosyası olusturuyor. oynatma exe’yi caliştirdiğimizda, event.json dosyasını import edip, yaptıgımız işlemi tekrar ediyor. işte bende bu işlemleri kendimiz durdurmadigimiz sürece sürekli tekrar etmesini istiyorum. umarım kendimi ifade edebilmişimdir.

from time import sleep
from keyboard import add_hotkey
durum=True
def durumdegistir():
    global durum
    durum=False
    print("İşlem durduruldu")
add_hotkey("esc",durumdegistir)
while durum:
    print("İşlem devam ediyor")
    sleep(1)

Anladığım kadarıyla böyle bir kod istiyorsunuz.

kodu çalıştırınca anladım galiba. esc ye basınca kod duruyor, sen kodun tekrar çalışmasını istiyosun galiba. Böyle yaparsak istediğin oluyo mu ?

# from pynput doc.
def on_release(key):
    try:
        print('{0} released'.format(
            key))
        if key == keyboard.Key.esc:
            print(time() - start_time)
            # returning False stops the keyboard listener, using stop function to stop mouse listener
            mouse_listener.stop()
            save_json()
            print('Fare ve klavye kaydı durduruldu..')
            run()
            return False
        save_event(current_time=round(time(), 2), action=1, key=key.char)
    except:
        save_event(current_time=round(time(), 2), action=1, key=str(key))

yok hocam, kayıt durduktan sonra, oynamak istediğimde, kaydettiğim işlemi döngüye sokup, biz durdurmadigimiz sürece, kaydettiğimiz işlemi sürekli tekrarlayacak.

Hocam Bu kod’da esc tusuna basılmadigi sürece kaydedilen işlemi sürekli tekrarlayacak değil mi?

Evet ama şimdi bi eksiklik fark ettim esc ye basılınca döngünün bitmesini bekliyor kırmak için düzeltmeye çalışıcam.

Bu tarz birşey olur mu peki ? :smiley: fareyi hareket ettiriyor. döngü bittikten sonra başa dönüyor gibi.

import pyautogui, time

def main():
    x = 0
    y = 0
    for i in range(5):
        pyautogui.move(x, y)
        x += 2
        y += 2
        time.sleep(0.5)
        
    if i == 4:
        x = 0
        y = 0
        main()

main()