Skip to content

Commit f435604

Browse files
committed
Nuovi giochi
1 parent 39e7308 commit f435604

28 files changed

+820
-0
lines changed

game14/README.md

Lines changed: 107 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,107 @@
1+
# 🃏 MEMO
2+
3+
Un classico gioco di memoria realizzato con **Python** e **Pygame Zero**, pensato per imparare a programmare giochi in modo semplice e divertente.
4+
5+
Parte del progetto [LearningPythonWithGames](https://github.com/PythonBiellaGroup/LearningPythonWithGames) di **Python Biella Group**.
6+
7+
---
8+
9+
## 🎮 Come si gioca
10+
11+
- Sul tavolo sono disposte **12 carte coperte** (6 coppie di colori).
12+
- Ogni turno, clicca su **due carte** per scoprirle.
13+
- Se i colori **coincidono** → la coppia resta visibile ✅
14+
- Se i colori **non coincidono** → le carte si rigirano dopo 2 secondi ❌
15+
- L'obiettivo è trovare tutte e 6 le coppie **nel minor numero di errori possibile**.
16+
- A partita completata, premi **SPAZIO** per ricominciare.
17+
18+
---
19+
20+
## 🖥️ Screenshot
21+
22+
![Screenshot del gioco](screenshot.png)
23+
24+
---
25+
26+
## 🚀 Installazione e avvio
27+
28+
### Prerequisiti
29+
30+
- Python 3.8 o superiore
31+
- `pgzero` (Pygame Zero)
32+
33+
### Installazione dipendenze
34+
35+
```bash
36+
pip install pgzero
37+
```
38+
39+
### Avvio del gioco
40+
41+
```bash
42+
python memo.py
43+
```
44+
45+
> ⚠️ Pygame Zero richiede che lo script venga avviato direttamente con `python`, non con `pgzrun` da riga di comando.
46+
47+
---
48+
49+
## 📁 Struttura del progetto
50+
51+
```
52+
memo.py # File principale del gioco (tutto in un unico file)
53+
README.md # Questo file
54+
```
55+
56+
---
57+
58+
## 🧠 Concetti Python trattati
59+
60+
Questo progetto è pensato a scopo **didattico**. Analizzando il codice si incontrano:
61+
62+
| Concetto | Dove |
63+
|---|---|
64+
| Variabili e costanti | Configurazione layout e colori |
65+
| Liste e indicizzazione | Gestione delle carte (`carte[idx]`) |
66+
| Funzioni | `crea_carte()`, `disegna_carta()`, `nascondi_carte()` |
67+
| Cicli `for` | Iterazione sulle carte da disegnare |
68+
| Condizioni `if/else` | Logica di gioco (coppia corretta o no) |
69+
| Stato globale | Variabili `errori`, `selezionate`, `partita_vinta` |
70+
| Callback e timer | `clock.schedule()` di Pygame Zero |
71+
| Shuffle casuale | `random.shuffle()` per rimescolare le carte |
72+
| Programmazione a eventi | `on_mouse_down()`, `on_key_down()` |
73+
74+
---
75+
76+
## ⚙️ Personalizzazione
77+
78+
Puoi modificare facilmente il comportamento del gioco cambiando le costanti in cima al file:
79+
80+
```python
81+
COLONNE = 6 # Numero di colonne della griglia
82+
DURATA_MOSTRA = 2 # Secondi prima di rigirare le carte sbagliate
83+
CARTA_W = 80 # Larghezza di ogni carta (pixel)
84+
CARTA_H = 110 # Altezza di ogni carta (pixel)
85+
```
86+
87+
Per aggiungere nuove coppie, aggiungi colori alla lista `COLORI` e aumenta `COLONNE` o il numero di righe di conseguenza.
88+
89+
---
90+
91+
## 📚 Risorse utili
92+
93+
- [Pygame Zero — documentazione ufficiale](https://pygame-zero.readthedocs.io/)
94+
- [Python Biella Group](https://pythonbiellagroup.it/)
95+
- [Repository LearningPythonWithGames](https://github.com/PythonBiellaGroup/LearningPythonWithGames)
96+
97+
---
98+
99+
## 🤝 Contribuire
100+
101+
Hai idee per migliorare il gioco o vuoi aggiungere una variante? Apri una **issue** o una **pull request** sulla repo principale!
102+
103+
---
104+
105+
## 📄 Licenza
106+
107+
Distribuito sotto licenza **MIT**. Vedi il file `LICENSE` nella repository principale per i dettagli.

game14/memo.pdf

1.93 MB
Binary file not shown.

game14/memo.py

Lines changed: 200 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,200 @@
1+
import random
2+
import pgzrun
3+
4+
# --- Finestra ---
5+
WIDTH = 700
6+
HEIGHT = 500
7+
TITLE = "MEMO"
8+
9+
# --- Layout ---
10+
COLONNE = 6
11+
CARTA_W = 80
12+
CARTA_H = 110
13+
SPAZIO_X = 20
14+
SPAZIO_Y = 30
15+
MARGINE_X = (WIDTH - COLONNE * CARTA_W - (COLONNE - 1) * SPAZIO_X) // 2
16+
MARGINE_Y = 110
17+
18+
# --- Colori delle 6 coppie ---
19+
COLORI = [
20+
(220, 60, 60), # rosso
21+
( 60, 160, 220), # azzurro
22+
( 60, 200, 100), # verde
23+
(230, 180, 40), # giallo
24+
(180, 80, 220), # viola
25+
(230, 120, 40), # arancione
26+
]
27+
28+
# --- Palette UI ---
29+
SFONDO = (30, 30, 40)
30+
CARTA_COPERTA = (60, 65, 90)
31+
CARTA_BORDO = (90, 95, 130)
32+
BIANCO = (255, 255, 255)
33+
GRIGIO = (180, 180, 200)
34+
TESTO_TITOLO = (200, 210, 255)
35+
VERDE_OK = ( 80, 220, 130)
36+
ROSSO_ERR = (220, 80, 80)
37+
38+
DURATA_MOSTRA = 2 # secondi prima di nascondere le carte sbagliate (usato da clock.schedule)
39+
40+
# =============================================================
41+
# Struttura carta: lista [colore_idx, scoperta, trovata, x, y]
42+
# colore_idx : int – indice in COLORI
43+
# scoperta : bool – temporaneamente visibile
44+
# trovata : bool – coppia indovinata, resta visibile
45+
# x, y : int – angolo superiore sinistro della carta
46+
# =============================================================
47+
48+
def crea_carte():
49+
indici = list(range(6)) * 2
50+
random.shuffle(indici)
51+
carte = []
52+
for i, idx_col in enumerate(indici):
53+
riga = i // COLONNE
54+
col = i % COLONNE
55+
x = MARGINE_X + col * (CARTA_W + SPAZIO_X)
56+
y = MARGINE_Y + riga * (CARTA_H + SPAZIO_Y)
57+
carte.append([idx_col, False, False, x, y])
58+
return carte
59+
60+
61+
# --- Stato globale ---
62+
carte = crea_carte()
63+
errori = 0
64+
selezionate = [] # indici delle carte scelte nel turno corrente (max 2)
65+
attesa_hide = False
66+
partita_vinta = False
67+
68+
# =============================================================
69+
# Disegno
70+
# =============================================================
71+
72+
def draw():
73+
screen.fill(SFONDO)
74+
75+
# Titolo
76+
screen.draw.text("MEMO", topleft=(28, 16),
77+
fontsize=42, color=TESTO_TITOLO, bold=True)
78+
79+
# Contatore errori
80+
col_err = ROSSO_ERR if errori > 0 else GRIGIO
81+
screen.draw.text(f"Errori: {errori}", topleft=(200, 26),
82+
fontsize=24, color=col_err)
83+
84+
# Suggerimento tasto spazio (solo durante il gioco)
85+
if partita_vinta:
86+
screen.draw.text("SPAZIO = nuova partita", topright=(WIDTH - 20, 26),
87+
fontsize=18, color=GRIGIO)
88+
89+
# Carte
90+
for carta in carte:
91+
disegna_carta(carta)
92+
93+
# Schermata di vittoria
94+
if partita_vinta:
95+
screen.draw.filled_rect(Rect(0, 0, WIDTH, HEIGHT), (20, 20, 35))
96+
screen.draw.text("Hai vinto!",
97+
center=(WIDTH // 2, HEIGHT // 2 - 35),
98+
fontsize=48, color=VERDE_OK, bold=True)
99+
screen.draw.text(f"Completato con {errori} errori",
100+
center=(WIDTH // 2, HEIGHT // 2 + 15),
101+
fontsize=26, color=BIANCO)
102+
screen.draw.text("Premi SPAZIO per giocare ancora",
103+
center=(WIDTH // 2, HEIGHT // 2 + 55),
104+
fontsize=18, color=GRIGIO)
105+
106+
107+
def disegna_carta(carta):
108+
idx_col, scoperta, trovata, x, y = carta
109+
r = Rect(x, y, CARTA_W, CARTA_H)
110+
111+
if scoperta or trovata:
112+
colore = COLORI[idx_col]
113+
screen.draw.filled_rect(r, colore)
114+
bordo = tuple(min(255, c + 70) for c in colore)
115+
screen.draw.rect(r, bordo)
116+
if trovata:
117+
screen.draw.rect(r, VERDE_OK)
118+
else:
119+
screen.draw.filled_rect(r, CARTA_COPERTA)
120+
screen.draw.rect(r, CARTA_BORDO)
121+
# Puntini decorativi sul retro
122+
for dr in range(3):
123+
for dc in range(3):
124+
px = x + CARTA_W // 4 + dc * (CARTA_W // 4)
125+
py = y + CARTA_H // 5 + dr * (CARTA_H // 4)
126+
screen.draw.filled_circle((px, py), 3, CARTA_BORDO)
127+
128+
129+
# =============================================================
130+
# Logica
131+
# =============================================================
132+
133+
def nascondi_carte():
134+
"""Chiamata da clock.schedule dopo DURATA_MOSTRA secondi."""
135+
global attesa_hide
136+
for idx in selezionate:
137+
carte[idx][1] = False # nascondi la carta
138+
selezionate.clear()
139+
attesa_hide = False
140+
141+
142+
def on_key_down(key):
143+
global errori, attesa_hide, selezionate, partita_vinta, carte
144+
145+
if key == keys.SPACE and partita_vinta:
146+
clock.unschedule(nascondi_carte)
147+
carte = crea_carte()
148+
errori = 0
149+
selezionate = []
150+
attesa_hide = False
151+
partita_vinta = False
152+
153+
154+
def on_mouse_down(pos):
155+
global errori, attesa_hide, selezionate, partita_vinta, carte
156+
157+
mx, my = pos
158+
159+
# Ignora clic durante attesa o a partita vinta
160+
if attesa_hide or partita_vinta:
161+
return
162+
163+
idx = indice_carta_sotto(mx, my)
164+
if idx == -1:
165+
return
166+
167+
carta = carte[idx]
168+
# Ignora carte già trovate, già scoperte o già selezionate
169+
if carta[2] or carta[1] or idx in selezionate:
170+
return
171+
172+
carta[1] = True # scopri la carta
173+
selezionate.append(idx)
174+
175+
if len(selezionate) == 2:
176+
idx_a, idx_b = selezionate
177+
if carte[idx_a][0] == carte[idx_b][0]:
178+
# Coppia corretta: segna come trovata
179+
carte[idx_a][2] = True
180+
carte[idx_b][2] = True
181+
selezionate = []
182+
if all(c[2] for c in carte):
183+
partita_vinta = True
184+
else:
185+
# Coppia sbagliata: incrementa errori e programma il nascondimento
186+
errori += 1
187+
attesa_hide = True
188+
clock.schedule(nascondi_carte, DURATA_MOSTRA)
189+
190+
191+
def indice_carta_sotto(mx, my):
192+
"""Restituisce l'indice della carta sotto il cursore, -1 se nessuna."""
193+
for i, carta in enumerate(carte):
194+
_, _, _, x, y = carta
195+
if x <= mx <= x + CARTA_W and y <= my <= y + CARTA_H:
196+
return i
197+
return -1
198+
199+
# Avvia il game loop di Pygame Zero
200+
pgzrun.go()

game14/screenshot.png

10.2 KB
Loading

0 commit comments

Comments
 (0)