Nota

Ciao, benvenuto nella Community di appassionati di Raspberry Pi, Arduino e ESP32 di SunFounder su Facebook! Approfondisci il mondo di Raspberry Pi, Arduino e ESP32 insieme ad altri appassionati.

Perché unirsi?

  • Supporto esperto: Risolvi problemi post-vendita e sfide tecniche con l’aiuto della nostra community e del nostro team.

  • Impara & Condividi: Scambia consigli e tutorial per migliorare le tue competenze.

  • Anteprime esclusive: Ottieni accesso anticipato agli annunci di nuovi prodotti e anteprime.

  • Sconti speciali: Approfitta di sconti esclusivi sui nostri prodotti più recenti.

  • Promozioni festive e giveaway: Partecipa a giveaway e promozioni festive.

👉 Pronto per esplorare e creare con noi? Clicca [Qui] e unisciti oggi stesso!

4.1.17 GIOCO – Indovina il Numero

Introduzione

«Indovina il Numero» è un gioco divertente da fare in gruppo, in cui tu e i tuoi amici vi alterniate nell’inserire un numero (0~99). L’intervallo numerico si riduce con l’inserimento del numero finché un giocatore non indovina correttamente l’enigma. Allora il giocatore viene sconfitto e punito. Ad esempio, se il numero fortunato è 51, che i giocatori non possono vedere, e il giocatore ① inserisce 50, l’intervallo numerico cambia a 50~99; se il giocatore ② inserisce 70, l’intervallo numerico diventa 50~70; se il giocatore ③ inserisce 51, questo giocatore è il «sfortunato». Qui utilizziamo il tastierino per inserire i numeri e l’LCD per mostrare i risultati.

Componenti Necessari

In questo progetto, ci servono i seguenti componenti.

../_images/list_GAME_Guess_Number.png

È sicuramente conveniente acquistare un intero kit, ecco il link:

Nome

ELEMENTI IN QUESTO KIT

LINK

Raphael Kit

337

Raphael Kit

Puoi anche acquistarli separatamente dai link qui sotto.

INTRODUZIONE COMPONENTE

LINK DI ACQUISTO

Scheda di estensione GPIO

ACQUISTA

Breadboard

ACQUISTA

Cavi Jumper

ACQUISTA

Resistore

ACQUISTA

Tastierino

-

I2C LCD1602

ACQUISTA

Schema Elettrico

T-Board Name

physical

wiringPi

BCM

GPIO18

Pin 12

1

18

GPIO23

Pin 16

4

23

GPIO24

Pin 18

5

24

GPIO25

Pin 22

6

25

SPIMOSI

Pin 19

12

10

GPIO22

Pin 15

3

22

GPIO27

Pin 13

2

27

GPIO17

Pin 11

0

17

SDA1

Pin 3

SDA1(8)

SDA1(2)

SCL1

Pin 5

SCL1(9)

SDA1(3)

../_images/Schematic_three_one12.png

Procedure Sperimentali

Passo 1: Costruisci il circuito.

../_images/image273.png

Passo 2: Configura I2C (vedi Configurazione I²C.)

Passo 3: Cambia directory.

cd ~/raphael-kit/python/

Passo 4: Esegui.

sudo python3 4.1.17_GAME_GuessNumber.py

Dopo l’avvio del programma, sulla LCD appare la pagina iniziale:

Welcome!
Press A to go!

Press ‘A’, and the game will start and the game page will appear on the LCD.

Inserisci numero:
0 ‹punto‹ 99

Un numero casuale “ punto“ viene generato ma non visualizzato sull’LCD quando il gioco inizia, e il tuo compito è indovinarlo. Il numero che hai digitato appare alla fine della prima riga fino a quando non viene effettuato il calcolo finale. (Premi “D” per avviare il confronto e se il numero inserito è maggiore di 10 , il confronto automatico inizia.)

L’intervallo numerico di “punto” viene visualizzato sulla seconda riga. Devi inserire il numero all’interno dell’intervallo. Quando inserisci un numero, l’intervallo si restringe; se indovini correttamente o meno, apparirà «L’hai preso!»

Nota

  • Se visualizzi l’errore FileNotFoundError: [Errno 2] No such file or directory: '/dev/i2c-1', devi fare riferimento a Configurazione I²C per abilitare l’I2C.

  • Se ricevi l’errore ModuleNotFoundError: No module named 'smbus2', esegui sudo apt install python3-smbus2.

  • Se compare l’errore OSError: [Errno 121] Remote I/O error, significa che il modulo è cablato in modo errato o è guasto.

  • Se il codice e il cablaggio sono corretti, ma l’LCD non mostra ancora contenuti, puoi regolare il potenziometro sul retro per aumentare il contrasto.

Codice

Nota

Puoi Modificare/Reimpostare/Copiare/Eseguire/Interrompere il codice qui sotto. Tuttavia, prima di fare ciò, devi accedere al percorso del codice sorgente come raphael-kit/python.

#!/usr/bin/env python3

import RPi.GPIO as GPIO
import time
import LCD1602
import random

##################### ECCO LA LIBRERIA KEYPAD TRASFERITA DA Arduino ############
#class Key:Definisci alcune delle proprietà di Key
class Keypad():

   def __init__(self, rowsPins, colsPins, keys):
      self.rowsPins = rowsPins
      self.colsPins = colsPins
      self.keys = keys
      GPIO.setwarnings(False)
      GPIO.setmode(GPIO.BCM)
      GPIO.setup(self.rowsPins, GPIO.OUT, initial=GPIO.LOW)
      GPIO.setup(self.colsPins, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)

   def read(self):
      pressed_keys = []
      for i, row in enumerate(self.rowsPins):
            GPIO.output(row, GPIO.HIGH)
            for j, col in enumerate(self.colsPins):
               index = i * len(self.colsPins) + j
               if (GPIO.input(col) == 1):
                  pressed_keys.append(self.keys[index])
            GPIO.output(row, GPIO.LOW)
      return pressed_keys

################ ESEMPIO DI CODICE INIZIA QUI ################

count = 0
pointValue = 0
upper=99
lower=0

def setup():
   global keypad, last_key_pressed,keys
   rowsPins = [18,23,24,25]
   colsPins = [10,22,27,17]
   keys = ["1","2","3","A",
            "4","5","6","B",
            "7","8","9","C",
            "*","0","#","D"]
   keypad = Keypad(rowsPins, colsPins, keys)
   last_key_pressed = []
   LCD1602.init(0x27, 1)    # init(slave address, luce di sfondo)
   LCD1602.clear()
   LCD1602.write(0, 0, 'Welcome!')
   LCD1602.write(0, 1, 'Press A to Start!')

def init_new_value():
   global pointValue,upper,count,lower
   pointValue = random.randint(0,99)
   upper = 99
   lower = 0
   count = 0
   print('point is %d' %(pointValue))

def detect_point():
   global count,upper,lower
   if count > pointValue:
      if count < upper:
            upper = count
   elif count < pointValue:
      if count > lower:
            lower = count
   elif count == pointValue:
      count = 0
      return 1
   count = 0
   return 0

def lcd_show_input(result):
   LCD1602.clear()
   if result == 1:
      LCD1602.write(0,1,'You have got it!')
      time.sleep(5)
      init_new_value()
      lcd_show_input(0)
      return
   LCD1602.write(0,0,'Enter number:')
   LCD1602.write(13,0,str(count))
   LCD1602.write(0,1,str(lower))
   LCD1602.write(3,1,' < Point < ')
   LCD1602.write(13,1,str(upper))

def loop():
   global keypad, last_key_pressed,count
   while(True):
      result = 0
      pressed_keys = keypad.read()
      if len(pressed_keys) != 0 and last_key_pressed != pressed_keys:
            if pressed_keys == ["A"]:
               init_new_value()
               lcd_show_input(0)
            elif pressed_keys == ["D"]:
               result = detect_point()
               lcd_show_input(result)
            elif pressed_keys[0] in keys:
               if pressed_keys[0] in list(["A","B","C","D","#","*"]):
                  continue
               count = count * 10
               count += int(pressed_keys[0])
               if count >= 10:
                  result = detect_point()
               lcd_show_input(result)
            print(pressed_keys)
      last_key_pressed = pressed_keys
      time.sleep(0.1)

# Definisci una funzione destroy per ripulire tutto dopo la fine dello script
def destroy():
   # Rilascia le risorse
   GPIO.cleanup()
   LCD1602.clear()

if __name__ == '__main__':     # Il programma inizia qui
   try:
      setup()
      while True:
            loop()
   except KeyboardInterrupt:   # Quando viene premuto 'Ctrl+C', il programma destroy() verrà eseguito.
      destroy()

Spiegazione del Codice

Nella parte iniziale del codice troviamo le funzioni operative di keypad e I2C LCD1602. Puoi approfondire maggiori dettagli su di esse nelle sezioni 1.1.7 LCD1602 I2C e 2.1.8 Tastierino.

Qui, quello che ci serve sapere è il seguente:

def init_new_value():
    global pointValue,upper,count,lower
    pointValue = random.randint(0,99)
    upper = 99
    lower = 0
    count = 0
    print('point is %d' %(pointValue))

La funzione genera il numero casuale ‘point’ e reimposta l’intervallo indicativo del numero.

def detect_point():
    global count,upper,lower
    if count > pointValue:
        if count < upper:
            upper = count
    elif count < pointValue:
        if count > lower:
            lower = count
    elif count == pointValue:
        count = 0
        return 1
    count = 0
    return 0

detect_point() confronta il numero inserito (count) con il numero generato “point”. Se il confronto indica che non sono uguali, count assegnerà valori a upper e lower e restituirà ‘0’; altrimenti, se sono uguali, verrà restituito ‘1’.

def lcd_show_input(result):
    LCD1602.clear()
    if result == 1:
        LCD1602.write(0,1,'You have got it!')
        time.sleep(5)
        init_new_value()
        lcd_show_input(0)
        return
    LCD1602.write(0,0,'Enter number:')
    LCD1602.write(13,0,str(count))
    LCD1602.write(0,1,str(lower))
    LCD1602.write(3,1,' < Point < ')
    LCD1602.write(13,1,str(upper))

Questa funzione serve a visualizzare la pagina del gioco.

str(count): Poiché write() supporta solo il tipo di dati — string, è necessario utilizzare str() per convertire il numero in string.

def loop():
    global keypad, last_key_pressed,count
    while(True):
        result = 0
        pressed_keys = keypad.read()
        if len(pressed_keys) != 0 and last_key_pressed != pressed_keys:
            if pressed_keys == ["A"]:
                init_new_value()
                lcd_show_input(0)
            elif pressed_keys == ["D"]:
                result = detect_point()
                lcd_show_input(result)
            elif pressed_keys[0] in keys:
                if pressed_keys[0] in list(["A","B","C","D","#","*"]):
                    continue
                count = count * 10
                count += int(pressed_keys[0])
                if count >= 10:
                    result = detect_point()
                lcd_show_input(result)
            print(pressed_keys)
        last_key_pressed = pressed_keys
        time.sleep(0.1)

main() contiene l’intero processo del programma, come mostrato di seguito:

  1. Inizializza I2C LCD1602 e Keypad.

  2. Verifica se il pulsante è stato premuto e ottieni la lettura del pulsante.

  3. Se viene premuto il pulsante ‘A’, comparirà un numero casuale 0-99 e il gioco inizierà.

  4. Se viene rilevato che il pulsante ‘D’ è stato premuto, il programma entrerà nella fase di giudizio del risultato.

  5. Se viene premuto un pulsante da 0-9, il valore di count cambierà; se count è maggiore di 10, allora inizierà il giudizio.

  6. Le variazioni del gioco e dei suoi valori vengono visualizzate su LCD1602.

Immagine del Fenomeno

../_images/image274.jpeg