IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Tkinter Python Discussion :

Fenetre qui crash a cause d'un clique (python version 3.10.11) [tkinter][pyautogui][time] [Python 3.X]


Sujet :

Tkinter Python

  1. #1
    Membre régulier
    Homme Profil pro
    Étudiant
    Inscrit en
    Janvier 2025
    Messages
    9
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 19
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Janvier 2025
    Messages : 9
    Par défaut Fenetre qui crash a cause d'un clique (python version 3.10.11) [tkinter][pyautogui][time]
    Bonjour, je cherche a me faire un petit auto clicker mais le problème est que quand je lance l'auto clicker ma fenêtre tkinter crash et ne répond plus donc pas moyen d'arrêter l'auto clique avec le bouton d'arrêt sur la fenêtre tkinter.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
     
    import tkinter as tk
    import pyautogui
    import time
     
    # Variable global qui dit si le clique est en marche ou non
    actif = False
     
    # Fonction qui clique avec un temps de repos entre
    def auto_click(interval):
        global actif
        while actif:
            pyautogui.click()
            time.sleep(interval)
     
    # Fonction pour démarrer l'auto-clicker
    def start_clicking():
        global actif
        actif = True
        try:
            interval = float(interval_entry.get())
        except ValueError: # Si pas de valeur donner par l'utilisateur initialiser a 1 seconde
            interval = 1
        auto_click(interval)
        t.start()
     
    # Fonction pour arrêter l'auto-clicker
    def stop_clicking():
        global actif
        actif = False
     
    # ########################################################################
    # Interface tkinter
     
    # Creation de la fenetre
    Fenetre1 = tk.Tk()
    Fenetre1.title("Auto Clicker")
     
    # Creation label pour le message de l'intervalle
    interval_label = tk.Label(Fenetre1, text="Intervalle (en secondes) :")
    interval_label.pack()
     
    # Creation de la zone de texte pour entrer l'intervalle
    interval_entry = tk.Entry(Fenetre1)
    interval_entry.pack()
     
    # Bouton pour démarrer l'auto-clicker
    start_button = tk.Button(Fenetre1, text="Démarrer", command=start_clicking)
    start_button.pack()
     
    # Bouton pour arrêter l'auto-clicker
    stop_button = tk.Button(Fenetre1, text="Arrêter", command=stop_clicking)
    stop_button.pack()
     
    # Interface Tkinter (infinie) pour le maintiens de la fenetre
    Fenetre1.mainloop()
    Merci de votre temps et de m'avoir écouter

  2. #2
    Expert confirmé
    Avatar de fred1599
    Homme Profil pro
    Lead Dev Python
    Inscrit en
    Juillet 2006
    Messages
    3 994
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Meurthe et Moselle (Lorraine)

    Informations professionnelles :
    Activité : Lead Dev Python
    Secteur : Arts - Culture

    Informations forums :
    Inscription : Juillet 2006
    Messages : 3 994
    Par défaut
    Hello,

    Ce code n'est pas testable, lors de l'appel à démarrer votre "autoclick" en appuyant sur le bouton "démarrer", on se rend compte de l'absence d'une variable t non définie.

    Autres problèmes,

    sleep est bloquant sur Tkinter, ne pas oublier que vous avez sur votre interface, une boucle événementielle qui tourne en boucle, faut pas la "déranger" avec cela, et ça vaut aussi pour la boucle infinie dans la fonction auto_click.

    Pour cela, il existe une méthode qui s'intègre dans cette boucle événementielle nommée after.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    def auto_click_tkinter():
        if actif:
            pyautogui.click()
            Fenetre1.after(1000, auto_click_tkinter)
    Celui qui trouve sans chercher est celui qui a longtemps cherché sans trouver.(Bachelard)
    La connaissance s'acquiert par l'expérience, tout le reste n'est que de l'information.(Einstein)

  3. #3
    Expert éminent
    Homme Profil pro
    Architecte technique retraité
    Inscrit en
    Juin 2008
    Messages
    21 586
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Manche (Basse Normandie)

    Informations professionnelles :
    Activité : Architecte technique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2008
    Messages : 21 586
    Par défaut
    Salut,
    Pour compléter ce qu'à déjà dit fred1599, la fonction
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    # Fonction pour démarrer l'auto-clicker
    def start_clicking():
        global actif
        actif = True
        try:
            interval = float(interval_entry.get())
        except ValueError: # Si pas de valeur donner par l'utilisateur initialiser a 1 seconde
            interval = 1
        auto_click(interval)
        t.start()
    entre dans une boucle infinie avec l'appel à auto_click. Du coup, l'instruction suivante qui devrait lever une exception de type NameError n'est jamais exécutée.... la fenêtre est gelée (elle ne crashe pas).

    Idée de code avec after qui fait un peu la même chose et qui vous montre 2/3 trucs:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    import tkinter as tk
    import pyautogui
     
    ident = None                    # after timer ident
     
    def do_click(interval):
        global ident
        pyautogui.click()
        ident = root.after(interval, do_click, interval)
     
     
    def clicking(start):
        global ident
     
        if start:
            try:
                interval = float(entry.get())
            except ValueError:
                interval = 1
            interval = int(interval*1000) # adjust for ms timer
            ident = root.after(interval, do_click, interval)
            button['text'] = 'Arrêter'
     
        else:
            root.after_cancel(ident)
            ident = None
            button['text'] = 'Démarrer'
     
    root = tk.Tk()
    root.title("Auto Clicker")
     
    tk.Label(root, text="Intervalle (en secondes) :").pack()
    entry = tk.Entry(root)
    entry.pack()
     
    button = tk.Button(root, text="Démarrer", command=lambda: clicking(not ident))
    button.pack()
     
    tk.mainloop()
    - W
    Architectures post-modernes.
    Python sur DVP c'est aussi des FAQs, des cours et tutoriels

  4. #4
    Membre régulier
    Homme Profil pro
    Étudiant
    Inscrit en
    Janvier 2025
    Messages
    9
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 19
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Janvier 2025
    Messages : 9
    Par défaut
    Citation Envoyé par fred1599 Voir le message
    Hello,

    Ce code n'est pas testable, lors de l'appel à démarrer votre "autoclick" en appuyant sur le bouton "démarrer", on se rend compte de l'absence d'une variable t non définie.

    Autres problèmes,

    sleep est bloquant sur Tkinter, ne pas oublier que vous avez sur votre interface, une boucle événementielle qui tourne en boucle, faut pas la "déranger" avec cela, et ça vaut aussi pour la boucle infinie dans la fonction auto_click.

    Pour cela, il existe une méthode qui s'intègre dans cette boucle événementielle nommée after.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    def auto_click_tkinter():
        if actif:
            pyautogui.click()
            Fenetre1.after(1000, auto_click_tkinter)
    Merci de votre réponse,
    Effectivement la variable t est en trop j'ai oublier de l'enlever. (c'était pour des test avec la bibliothèque threading se qui nuisait a la précision de mon clique alors je l'ai mis de coter)
    Pour ce qui est de la sleep je ne savais pas qu'il interférait avec tkinter merci de cette information. Il faut aussi que je revois la notion de "déranger" mes boucle ca je n'avais jamais eu a faire à ce problème auparavant.

  5. #5
    Membre régulier
    Homme Profil pro
    Étudiant
    Inscrit en
    Janvier 2025
    Messages
    9
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 19
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Janvier 2025
    Messages : 9
    Par défaut
    Citation Envoyé par wiztricks Voir le message
    Salut,
    Pour compléter ce qu'à déjà dit fred1599, la fonction
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    # Fonction pour démarrer l'auto-clicker
    def start_clicking():
        global actif
        actif = True
        try:
            interval = float(interval_entry.get())
        except ValueError: # Si pas de valeur donner par l'utilisateur initialiser a 1 seconde
            interval = 1
        auto_click(interval)
        t.start()
    entre dans une boucle infinie avec l'appel à auto_click. Du coup, l'instruction suivante qui devrait lever une exception de type NameError n'est jamais exécutée.... la fenêtre est gelée (elle ne crashe pas).

    Idée de code avec after qui fait un peu la même chose et qui vous montre 2/3 trucs:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    import tkinter as tk
    import pyautogui
     
    ident = None                    # after timer ident
     
    def do_click(interval):
        global ident
        pyautogui.click()
        ident = root.after(interval, do_click, interval)
     
     
    def clicking(start):
        global ident
     
        if start:
            try:
                interval = float(entry.get())
            except ValueError:
                interval = 1
            interval = int(interval*1000) # adjust for ms timer
            ident = root.after(interval, do_click, interval)
            button['text'] = 'Arrêter'
     
        else:
            root.after_cancel(ident)
            ident = None
            button['text'] = 'Démarrer'
     
    root = tk.Tk()
    root.title("Auto Clicker")
     
    tk.Label(root, text="Intervalle (en secondes) :").pack()
    entry = tk.Entry(root)
    entry.pack()
     
    button = tk.Button(root, text="Démarrer", command=lambda: clicking(not ident))
    button.pack()
     
    tk.mainloop()
    - W
    Merci de vote réponse,
    J'ai compris pourquoi ma fenêtre gelai grâce a vous, et merci de votre proposition de code.

    Néanmoins je n'ai pas tout compris du fonctionnement sur votre code :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    ident = root.after(interval, do_click, interval)
    Pourquoi y'a t'il 2 fois l'interval dans les arguments de cette fonction
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    root.after(delay, callback_function, *args)
    j'ai trouver cette explication à ce sujet mais pas très claire non plus je trouve


    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    button = tk.Button(root, text="Démarrer", command=lambda: clicking(not ident))
    de même dans cette partie je ne comprend pas l'utilisation du lambda
    (l'utilisation du "not ident" est très bien penser c'est rare que j'utilise not).

  6. #6
    Expert éminent
    Homme Profil pro
    Architecte technique retraité
    Inscrit en
    Juin 2008
    Messages
    21 586
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Manche (Basse Normandie)

    Informations professionnelles :
    Activité : Architecte technique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2008
    Messages : 21 586
    Par défaut
    Citation Envoyé par Devoghlockst Voir le message
    Pourquoi y'a t'il 2 fois l'interval dans les arguments de cette fonction
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    root.after(delay, callback_function, *args)
    j'ai trouver cette explication à ce sujet mais pas très claire non plus je trouve
    Le premier correspond à delay et le second au premier de la liste *args.

    Citation Envoyé par Devoghlockst Voir le message
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    button = tk.Button(root, text="Démarrer", command=lambda: clicking(not ident))
    de même dans cette partie je ne comprend pas l'utilisation du lambda
    La fonction doit être appelée avec un argument lorsqu'on clique sur le Button pas avant.
    lambda permet de créer cette fonction... où la valeur du paramètre sera évaluée au moment de l'appel.

    - W
    Architectures post-modernes.
    Python sur DVP c'est aussi des FAQs, des cours et tutoriels

  7. #7
    Membre régulier
    Homme Profil pro
    Étudiant
    Inscrit en
    Janvier 2025
    Messages
    9
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 19
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Janvier 2025
    Messages : 9
    Par défaut
    Citation Envoyé par wiztricks Voir le message
    Le premier correspond à delay et le second au premier de la liste *args.



    La fonction doit être appelée avec un argument lorsqu'on clique sur le Button pas avant.
    lambda permet de créer cette fonction... où la valeur du paramètre sera évaluée au moment de l'appel.

    - W
    D'accord merci beaucoup pour ses explication je vais pouvoir continuer mon petit programme avec tous vos conseils et explications

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Des fenêtres qui s'ouvrent la ou on les clique ?
    Par Yepazix dans le forum Windows
    Réponses: 1
    Dernier message: 09/10/2017, 11h50
  2. Probleme Jeu qui Crash a Cause De Java
    Par FuniiX dans le forum Hardware
    Réponses: 3
    Dernier message: 09/04/2017, 11h16
  3. fenêtre qui disparaît lorsque l'on clique ailleurs que sur elle
    Par Thor Tillas dans le forum Windows Presentation Foundation
    Réponses: 7
    Dernier message: 17/07/2008, 16h18
  4. fenetre qui fuit la souris
    Par Nurs dans le forum C++Builder
    Réponses: 4
    Dernier message: 03/11/2004, 00h58
  5. [MFC] Ces fenêtres qui ne s'affichent pas..
    Par Davide dans le forum MFC
    Réponses: 3
    Dernier message: 19/11/2003, 12h30

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo