Skip to content

Add test cases #309

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 2 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
160 changes: 102 additions & 58 deletions Caterpillar_Game/Caterpillar.py
Original file line number Diff line number Diff line change
@@ -1,136 +1,180 @@
import turtle as t
import random as rd

# Set the background color
t.bgcolor('yellow')

# Caterpillar setup
caterpillar = t.Turtle()
caterpillar.shape('square')
caterpillar.speed(0)
caterpillar.penup()
caterpillar.hideturtle()

# Leaf setup
leaf = t.Turtle()
leaf_shape = ((0,0),(14,2),(18,6),(20,20),(6,18),(2,14))
leaf_shape = ((0, 0), (14, 2), (18, 6), (20, 20), (6, 18), (2, 14))
t.register_shape('leaf', leaf_shape)
leaf.shape('leaf')
leaf.color('green')
leaf.penup()
leaf.hideturtle()
leaf.speed()

game_started = False
text_turtle = False
# Text setup
text_turtle = t.Turtle()
text_turtle.write('Press SPACE to start', align='center', font=('Arial', 18, 'bold'))
text_turtle.hideturtle()

# Score setup
score_turtle = t.Turtle()
score_turtle.hideturtle()
score_turtle.speed(0)

obstacle = t.Turtle()
obstacle.shape('circle') # You can choose any shape
obstacle.color('red') # Choose a distinct color for obstacles
obstacle.penup()
obstacle.hideturtle()

num_obstacles = 5 # Number of obstacles
obstacles = []

for _ in range(num_obstacles):
new_obstacle = t.Turtle()
new_obstacle.shape('circle')
new_obstacle.color('red')
new_obstacle.penup()
new_obstacle.setposition(rd.randint(-200, 200), rd.randint(-200, 200))
new_obstacle.showturtle()
obstacles.append(new_obstacle)
# Game state variables
game_started = False


def outside_window():
left_wall = -t.window_width()/2
right_Wall = t.window_width()/2
top_wall = t.window_height()/2
bottom_wall = -t.window_height()/2
(x,y) = caterpillar.pos()
outside = x < left_wall or x > right_Wall or y > top_wall or y < bottom_wall
"""Check if the caterpillar is outside the window."""
left_wall = -t.window_width() / 2
right_wall = t.window_width() / 2
top_wall = t.window_height() / 2
bottom_wall = -t.window_height() / 2
(x, y) = caterpillar.pos()
outside = x < left_wall or x > right_wall or y > top_wall or y < bottom_wall
return outside


def game_over():
"""Handle game over scenario."""
caterpillar.color('yellow')
leaf.color('yellow')
t.penup()
t.hideturtle()
t.write('GAME OVER !', align='center', font=('Arial', 30, 'normal') )
t.onkey(start_game,'space')
t.write('GAME OVER!', align='center', font=('Arial', 30, 'normal'))
t.onkey(start_game, 'space') # Allow the user to restart the game by pressing SPACE


def display_score(current_score):
"""Display the score on the screen."""
score_turtle.clear()
score_turtle.penup()
x = (t.window_width()/2) - 70
y = (t.window_height()/2) - 70
score_turtle.setpos(x,y)
x = (t.window_width() / 2) - 70
y = (t.window_height() / 2) - 70
score_turtle.setpos(x, y)
score_turtle.write(str(current_score), align='right', font=('Arial', 40, 'bold'))


def place_leaf():
"""Randomly place the leaf on the screen."""
leaf.hideturtle()
leaf.setx(rd.randint(-200,200))
leaf.sety(rd.randint(-200,200))
leaf.setx(rd.randint(-200, 200))
leaf.sety(rd.randint(-200, 200))
leaf.showturtle()


def start_game():
"""Start the game."""
global game_started
if game_started:
return
game_started = True

score = 0
text_turtle.clear()

caterpillar_speed = 2
# Reset game state
caterpillar_length = 3
caterpillar.shapesize(1,caterpillar_length,1)
caterpillar.shapesize(1, caterpillar_length, 1)
caterpillar.showturtle()
caterpillar.color('black')
score = 0
caterpillar_speed = 2
text_turtle.clear()

# Reset caterpillar position
caterpillar.penup()
caterpillar.setpos(0, 0)
caterpillar.setheading(0)

# Display initial score and place the first leaf
display_score(score)
place_leaf()

while True:
caterpillar.forward(caterpillar_speed)
for obstacle in obstacles:
if caterpillar.distance(leaf) < 20:
place_leaf()
caterpillar_length = caterpillar_length + 1
caterpillar.shapesize(1,caterpillar_length,1)
caterpillar_speed = caterpillar_speed + 1
score = score + 10
display_score(score)
game_over()
break

# Check if the caterpillar eats the leaf
if caterpillar.distance(leaf) < 20:
place_leaf()
caterpillar_length = caterpillar_length + 1
caterpillar.shapesize(1, caterpillar_length, 1)
caterpillar_speed = caterpillar_speed + 1
score = score + 10
display_score(score)

# Check if the caterpillar is outside the window
if outside_window():
game_over()
break


def move_up():
if caterpillar.heading() != 270:
caterpillar.setheading(90)


def move_down():
if caterpillar.heading() != 90:
caterpillar.setheading(270)


def move_left():
if caterpillar.heading() != 0:
caterpillar.setheading(180)


def move_right():
if caterpillar.heading() != 180:
caterpillar.setheading(0)



def restart_game():
start_game()

t.onkey(start_game,'space')
t.onkey(restart_game,'Up')
t.onkey(move_up,'Up')
t.onkey(move_right,'Right')
t.onkey(move_down,'Down')
t.onkey(move_left,'Left')
"""Restart the game when 'R' is pressed."""
global game_started
if game_started:
game_started = False
caterpillar.hideturtle()
leaf.hideturtle()
score_turtle.clear()
text_turtle.clear()
t.clear() # Clear any game over text
start_game()


# Bind keys
t.onkey(start_game, 'space')
t.onkey(restart_game, 'r')
t.onkey(move_up, 'Up')
t.onkey(move_right, 'Right')
t.onkey(move_down, 'Down')
t.onkey(move_left, 'Left')

# Listen to the keyboard inputs
t.listen()

# Add some assert-based tests for the game logic
def test_outside_window():
"""Test the outside_window function."""
# Move caterpillar to an out-of-bounds position
caterpillar.setpos(1000, 1000)
assert outside_window() == True, "Caterpillar should be outside the window."

# Move caterpillar to an in-bounds position
caterpillar.setpos(0, 0)
assert outside_window() == False, "Caterpillar should be inside the window."
print("test_outside_window passed.")

# Run tests
test_outside_window()

# Start the main loop
t.mainloop()
65 changes: 65 additions & 0 deletions Caterpillar_Game/test_caterpillar.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
import unittest
from unittest.mock import patch, MagicMock
import caterpillar

class TestCaterpillarGame(unittest.TestCase):

def setUp(self):
"""在每个测试之前运行"""
self.caterpillar = caterpillar.caterpillar

@patch('caterpillar.t.Turtle')
def test_start_game(self, MockTurtle):
"""测试开始游戏"""
mock_turtle = MockTurtle()
caterpillar.start_game()

# 验证调用了显示初始得分的方法
self.assertTrue(mock_turtle.write.called, "Failed to display score at the start.")

def test_outside_window(self):
"""测试毛毛虫是否在窗口外"""
# 设置位置为窗口边界外
self.caterpillar.setx(caterpillar.t.window_width() / 2 + 10)
self.caterpillar.sety(caterpillar.t.window_height() / 2 + 10)

# 使用断言来检查
self.assertTrue(caterpillar.outside_window(), "Caterpillar should be outside the window.")

@patch('caterpillar.t.Turtle')
def test_move_up(self, MockTurtle):
"""测试毛毛虫向上移动"""
caterpillar.caterpillar.setheading(0) # Initially set to right
caterpillar.move_up()
self.assertEqual(caterpillar.caterpillar.heading(), 90, "Caterpillar did not change heading to up correctly.")

@patch('caterpillar.t.Turtle')
def test_move_down(self, MockTurtle):
"""测试毛毛虫向下移动"""
caterpillar.caterpillar.setheading(0) # Initially set to right
caterpillar.move_down()
self.assertEqual(caterpillar.caterpillar.heading(), 270, "Caterpillar did not change heading to down correctly.")

@patch('caterpillar.t.Turtle')
def test_move_left(self, MockTurtle):
"""测试毛毛虫向左移动"""
caterpillar.caterpillar.setheading(90) # Initially set to up
caterpillar.move_left()
self.assertEqual(caterpillar.caterpillar.heading(), 180, "Caterpillar did not change heading to left correctly.")

@patch('caterpillar.t.Turtle')
def test_move_right(self, MockTurtle):
"""测试毛毛虫向右移动"""
caterpillar.caterpillar.setheading(180) # Initially set to left
caterpillar.move_right()
self.assertEqual(caterpillar.caterpillar.heading(), 0, "Caterpillar did not change heading to right correctly.")

@patch('caterpillar.t.Turtle')
def test_place_leaf(self, MockTurtle):
"""测试随机放置叶子"""
mock_leaf = MockTurtle()
caterpillar.place_leaf()
self.assertTrue(mock_leaf.showturtle.called, "Leaf was not displayed after placing.")

if __name__ == '__main__':
unittest.main()