.. note:: Bonjour et bienvenue dans la Communauté Facebook des passionnés de Raspberry Pi, Arduino et ESP32 de SunFounder ! Plongez plus profondément dans l'univers des Raspberry Pi, Arduino et ESP32 avec d'autres passionnés. **Pourquoi rejoindre ?** - **Support d'experts** : Résolvez les problèmes après-vente et les défis techniques avec l'aide de notre communauté et de notre équipe. - **Apprendre et partager** : Échangez des astuces et des tutoriels pour améliorer vos compétences. - **Aperçus exclusifs** : Accédez en avant-première aux annonces de nouveaux produits et aux aperçus. - **Réductions spéciales** : Profitez de réductions exclusives sur nos produits les plus récents. - **Promotions festives et cadeaux** : Participez à des cadeaux et des promotions de vacances. 👉 Prêt à explorer et à créer avec nous ? Cliquez [|link_sf_facebook|] et rejoignez-nous aujourd'hui ! .. _4.1.18_py_pi5: 4.1.15 JEU - 10 Secondes ============================ Introduction ------------------- Ensuite, suivez-moi pour créer un dispositif de jeu qui mettra au défi votre concentration. Attachez l'interrupteur à bascule à un bâton pour en faire une baguette magique. Agitez la baguette, l'affichage à 4 chiffres commencera à compter, une nouvelle secousse arrêtera le comptage. Si vous réussissez à maintenir le compte affiché à **10.00**, alors vous gagnez. Vous pouvez jouer à ce jeu avec vos amis pour voir qui est le sorcier du temps. Composants nécessaires ------------------------------ Pour ce projet, nous avons besoin des composants suivants. .. image:: ../python_pi5/img/4.1.18_game_10_second_list.png :width: 800 :align: center Il est certainement pratique d'acheter un kit complet, voici le lien : .. list-table:: :widths: 20 20 20 :header-rows: 1 * - Nom - ARTICLES DANS CE KIT - LIEN * - Kit Raphael - 337 - |link_Raphael_kit| Vous pouvez également les acheter séparément via les liens ci-dessous. .. list-table:: :widths: 30 20 :header-rows: 1 * - INTRODUCTION DU COMPOSANT - LIEN D'ACHAT * - :ref:`cpn_gpio_extension_board` - |link_gpio_board_buy| * - :ref:`cpn_breadboard` - |link_breadboard_buy| * - :ref:`cpn_wires` - |link_wires_buy| * - :ref:`cpn_resistor` - |link_resistor_buy| * - :ref:`cpn_4_digit` - \- * - :ref:`cpn_74hc595` - |link_74hc595_buy| * - :ref:`cpn_tilt_switch` - \- Schéma ------------------------ ============ ======== ======== === Nom T-Board physique wiringPi BCM GPIO17 Pin 11 0 17 GPIO27 Pin 13 2 27 GPIO22 Pin 15 3 22 SPIMOSI Pin 19 12 10 GPIO18 Pin 12 1 18 GPIO23 Pin 16 4 23 GPIO24 Pin 18 5 24 GPIO26 Pin 37 25 26 ============ ======== ======== === .. image:: ../python_pi5/img/4.1.18_game_10_second_schematic.png :align: center Procédures expérimentales --------------------------------- **Étape 1** : Construisez le circuit. .. image:: ../python_pi5/img/4.1.18_game_10_second_circuit.png **Étape 2** : Accédez au dossier du code. .. raw:: html .. code-block:: cd ~/raphael-kit/python-pi5 **Étape 3** : Exécutez le fichier exécutable. .. raw:: html .. code-block:: sudo python3 4.1.18_GAME_10Second_zero.py Secouez la baguette, l'affichage à 4 chiffres commencera à compter, secouez à nouveau pour arrêter le comptage. Si vous réussissez à maintenir le compte affiché à **10.00**, alors vous gagnez. Secouez-la une fois de plus pour commencer la prochaine manche du jeu. .. warning:: Si vous recevez le message d'erreur ``RuntimeError: Cannot determine SOC peripheral base address``, veuillez consulter :ref:`faq_soc` **Code** .. note:: Vous pouvez **modifier/réinitialiser/copier/exécuter/arrêter** le code ci-dessous. Mais avant cela, vous devez vous rendre au chemin du code source comme ``raphael-kit/python-pi5``. Après avoir modifié le code, vous pouvez l'exécuter directement pour voir l'effet. .. raw:: html .. code-block:: python #!/usr/bin/env python3 from gpiozero import OutputDevice, Button import time import threading # Initialize the button connected to GPIO 26 sensorPin = Button(26) # Define GPIO pins connected to the 74HC595 shift register SDI = OutputDevice(24) # Serial Data Input RCLK = OutputDevice(23) # Register Clock SRCLK = OutputDevice(18) # Shift Register Clock # Define GPIO pins for digit selection on the 7-segment display placePin = [OutputDevice(pin) for pin in (10, 22, 27, 17)] # Define segment codes for numbers 0 to 9 on the 7-segment display number = (0xc0, 0xf9, 0xa4, 0xb0, 0x99, 0x92, 0x82, 0xf8, 0x80, 0x90) # Counter and timer variables counter = 0 timer1 = None gameState = 0 def clearDisplay(): """ Clear all segments on the 7-segment display. """ for _ in range(8): SDI.on() SRCLK.on() SRCLK.off() RCLK.on() RCLK.off() def hc595_shift(data): """ Shift data to the 74HC595 shift register to display a digit. """ for i in range(8): SDI.value = 0x80 & (data << i) SRCLK.on() SRCLK.off() RCLK.on() RCLK.off() def pickDigit(digit): """ Select which digit to display on the 7-segment display. """ for pin in placePin: pin.off() placePin[digit].on() def display(): """ Display the current counter value on the 7-segment display. """ global counter clearDisplay() pickDigit(0) hc595_shift(number[counter % 10]) clearDisplay() pickDigit(1) hc595_shift(number[counter % 100 // 10]) clearDisplay() pickDigit(2) hc595_shift(number[counter % 1000 // 100] - 0x80) clearDisplay() pickDigit(3) hc595_shift(number[counter % 10000 // 1000]) def stateChange(): """ Handle state changes for the counter based on button presses. """ global gameState, counter, timer1 if gameState == 0: counter = 0 time.sleep(1) timer() elif gameState == 1 and timer1 is not None: timer1.cancel() time.sleep(1) gameState = (gameState + 1) % 2 def loop(): """ Main loop to check for button presses and update the display. """ global counter currentState = 0 lastState = 0 while True: display() currentState = sensorPin.value if (currentState == 0) and (lastState == 1): stateChange() lastState = currentState def timer(): """ Timer function that increments the counter every 0.01 second. """ global counter, timer1 timer1 = threading.Timer(0.01, timer) timer1.start() counter += 1 try: loop() except KeyboardInterrupt: if timer1: timer1.cancel() **Explication du code** #. Le script commence par importer les modules nécessaires. La bibliothèque ``gpiozero`` est utilisée pour interagir avec les dispositifs GPIO comme les boutons, et les modules ``time`` et ``threading`` peuvent être utilisés pour gérer des tâches liées au temps ou des opérations concurrentes. .. code-block:: python #!/usr/bin/env python3 from gpiozero import OutputDevice, Button import time import threading #. Initialise un objet ``Button`` de la bibliothèque GPIO Zero, connecté à la broche GPIO 26. Cette configuration permet de détecter les pressions sur le bouton. .. code-block:: python # Initialize the button connected to GPIO 26 sensorPin = Button(26) #. Initialise les broches GPIO connectées aux entrées de données série (SDI), d'horloge du registre (RCLK) et d'horloge du registre à décalage (SRCLK) du registre à décalage. .. code-block:: python # Define GPIO pins connected to the 74HC595 shift register SDI = OutputDevice(24) # Serial Data Input RCLK = OutputDevice(23) # Register Clock SRCLK = OutputDevice(18) # Shift Register Clock #. Initialise les broches pour chaque chiffre de l'affichage à 7 segments et définit les codes binaires pour afficher les nombres de 0 à 9. .. code-block:: python # Define GPIO pins for digit selection on the 7-segment display placePin = [OutputDevice(pin) for pin in (10, 22, 27, 17)] # Define segment codes for numbers 0 to 9 on the 7-segment display number = (0xc0, 0xf9, 0xa4, 0xb0, 0x99, 0x92, 0x82, 0xf8, 0x80, 0x90) #. Fonctions pour contrôler l'affichage à 7 segments. ``clearDisplay`` éteint tous les segments, ``hc595_shift`` transfère les données dans le registre à décalage, et ``pickDigit`` active un chiffre spécifique sur l'affichage. .. code-block:: python def clearDisplay(): """ Clear all segments on the 7-segment display. """ for _ in range(8): SDI.on() SRCLK.on() SRCLK.off() RCLK.on() RCLK.off() def hc595_shift(data): """ Shift data to the 74HC595 shift register to display a digit. """ for i in range(8): SDI.value = 0x80 & (data << i) SRCLK.on() SRCLK.off() RCLK.on() RCLK.off() def pickDigit(digit): """ Select which digit to display on the 7-segment display. """ for pin in placePin: pin.off() placePin[digit].on() #. Fonction pour afficher la valeur actuelle du compteur sur l'affichage à 7 segments. .. code-block:: python def display(): """ Display the current counter value on the 7-segment display. """ global counter clearDisplay() pickDigit(0) hc595_shift(number[counter % 10]) clearDisplay() pickDigit(1) hc595_shift(number[counter % 100 // 10]) clearDisplay() pickDigit(2) hc595_shift(number[counter % 1000 // 100] - 0x80) clearDisplay() pickDigit(3) hc595_shift(number[counter % 10000 // 1000]) #. Fonction pour gérer les changements d'état (démarrage/arrêt) du compteur en fonction des pressions sur le bouton. .. code-block:: python def stateChange(): """ Handle state changes for the counter based on button presses. """ global gameState, counter, timer1 if gameState == 0: counter = 0 time.sleep(1) timer() elif gameState == 1 and timer1 is not None: timer1.cancel() time.sleep(1) gameState = (gameState + 1) % 2 #. Boucle principale qui vérifie en continu l'état du bouton et met à jour l'affichage. Elle appelle ``stateChange`` lorsque l'état du bouton change. .. code-block:: python def loop(): """ Main loop to check for button presses and update the display. """ global counter currentState = 0 lastState = 0 while True: display() currentState = sensorPin.value if (currentState == 0) and (lastState == 1): stateChange() lastState = currentState #. Fonction de minuterie qui incrémente le compteur à intervalle régulier (toutes les 0,01 seconde). .. code-block:: python def timer(): """ Timer function that increments the counter every 0.01 second. """ global counter, timer1 timer1 = threading.Timer(0.01, timer) timer1.start() counter += 1 #. Exécute la boucle principale et permet une sortie propre du programme à l'aide d'une interruption du clavier (Ctrl+C). .. code-block:: python try: loop() except KeyboardInterrupt: if timer1: timer1.cancel()