-
Notifications
You must be signed in to change notification settings - Fork 0
/
gestured_snake.py
157 lines (125 loc) · 4.21 KB
/
gestured_snake.py
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
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
#
# Copyright 2023 Krzysztof Hoszowski
#
# This file is part of Gestured Snake.
#
# Gestured Snake is free software: you can redistribute it and/or
# modify it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Gestured Snake is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
# Public License for more details.
#
# You should have received a copy of the GNU General Public License along
# with Gestured Snake. If not, see <https://www.gnu.org/licenses/>.
#
#
"""Snake terminal game controlled using hand gestures."""
# Calculating results of AI model
from statistics import mode
# Loading AI model
from joblib import load
# Getting images from webcam
from cv2 import VideoCapture, imwrite
# Obtaining dataframes from images
from pd2img import Pd2Img
# Preprocessing images
from extract_hand import extract_hand
# Basic variables and functions
from snake import *
# Preparing webcam
WEBCAM_PORT = 0
webcam = VideoCapture(WEBCAM_PORT)
# Adjusting game speed to gesture controls
SNAKE_SPEED = 5
# Loading AI classifier
clf = load("model.pkl")
# Controls variable
prediction = -1
# Limiting controls speed
counter = 0
### Main Program Loop ###
while True:
counter += 1
if counter == 2:
# Resetting the timer
counter = 0
# Reading input using the camera
result, image = webcam.read()
if result:
# Extracting the hand
mask = extract_hand(image)
imwrite("mask.png", mask)
# Convert mask to dataframe
df = Pd2Img("mask.png")
# Recognizing the gesture
predictions = clf.predict(df.df.iloc[:, 0:3])
prediction = mode(predictions)
print(prediction)
if prediction == 1:
dir_index += 1
dir_index %= 4
elif prediction == 2:
dir_index -= 1
dir_index %= 4
else:
print("No image detected. Please check your camera or settings.")
# Alternative to webcam: Handling key events
for event in pygame.event.get():
if event.type == pygame.KEYDOWN:
if event.key == pygame.K_UP:
dir_index += 1
dir_index %= 4
if event.key == pygame.K_DOWN:
dir_index -= 1
dir_index %= 4
# Moving the snake
if directions[dir_index] == "UP":
snake_position[1] -= 10
if directions[dir_index] == "DOWN":
snake_position[1] += 10
if directions[dir_index] == "LEFT":
snake_position[0] -= 10
if directions[dir_index] == "RIGHT":
snake_position[0] += 10
# Snake body growing mechanism
# If fruit and snake collide then score will be incremented by 10
snake_body.insert(0, list(snake_position))
if (
snake_position[0] == fruit_position[0]
and snake_position[1] == fruit_position[1]
):
score += 10
fruit_spawn = False
else:
snake_body.pop()
if not fruit_spawn:
fruit_position = [
randrange(1, (WINDOW_X // 10)) * 10,
randrange(1, (WINDOW_Y // 10)) * 10,
]
fruit_spawn = True
game_window.fill(BLACK)
for pos in snake_body:
pygame.draw.rect(game_window, GREEN, pygame.Rect(pos[0], pos[1], 10, 10))
pygame.draw.rect(
game_window, WHITE, pygame.Rect(fruit_position[0], fruit_position[1], 10, 10)
)
# Game Over conditions
if snake_position[0] < 0 or snake_position[0] > WINDOW_X - 10:
game_over(score)
if snake_position[1] < 0 or snake_position[1] > WINDOW_Y - 10:
game_over(score)
# Touching the snake body
for block in snake_body[1:]:
if snake_position[0] == block[0] and snake_position[1] == block[1]:
game_over(score)
# Displaying score
show_score(score, WHITE, "calibri", 20)
# Refresh game screen
pygame.display.update()
# Frame Per Second / Refresh Rate
fps.tick(SNAKE_SPEED)