Bez popisu

game_functions.py 8.3KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239
  1. import sys
  2. from time import sleep
  3. import pygame
  4. from bullet import Bullet
  5. from alien import Alien
  6. def check_keydown_events(event, ai_settings, screen, ship, bullets):
  7. """Respond to keypresses."""
  8. if event.key == pygame.K_RIGHT:
  9. ship.moving_right = True
  10. elif event.key == pygame.K_LEFT:
  11. ship.moving_left = True
  12. elif event.key == pygame.K_SPACE:
  13. fire_bullet(ai_settings, screen, ship, bullets)
  14. elif event.key == pygame.K_q:
  15. sys.exit()
  16. def check_keyup_events(event, ship):
  17. """Respond to key releases."""
  18. if event.key == pygame.K_RIGHT:
  19. ship.moving_right = False
  20. elif event.key == pygame.K_LEFT:
  21. ship.moving_left = False
  22. def check_events(ai_settings, screen, stats, sb, play_button, ship, aliens,
  23. bullets):
  24. """Respond to keypresses and mouse events."""
  25. for event in pygame.event.get():
  26. if event.type == pygame.QUIT:
  27. sys.exit()
  28. elif event.type == pygame.KEYDOWN:
  29. check_keydown_events(event, ai_settings, screen, ship, bullets)
  30. elif event.type == pygame.KEYUP:
  31. check_keyup_events(event, ship)
  32. elif event.type == pygame.MOUSEBUTTONDOWN:
  33. mouse_x, mouse_y = pygame.mouse.get_pos()
  34. check_play_button(ai_settings, screen, stats, sb, play_button,
  35. ship, aliens, bullets, mouse_x, mouse_y)
  36. def check_play_button(ai_settings, screen, stats, sb, play_button, ship,
  37. aliens, bullets, mouse_x, mouse_y):
  38. """Start a new game when the player clicks Play."""
  39. button_clicked = play_button.rect.collidepoint(mouse_x, mouse_y)
  40. if button_clicked and not stats.game_active:
  41. # Reset the game settings.
  42. ai_settings.initialize_dynamic_settings()
  43. # Hide the mouse cursor.
  44. pygame.mouse.set_visible(False)
  45. # Reset the game statistics.
  46. stats.reset_stats()
  47. stats.game_active = True
  48. # Reset the scoreboard images.
  49. sb.prep_score()
  50. sb.prep_high_score()
  51. sb.prep_level()
  52. sb.prep_ships()
  53. # Empty the list of aliens and bullets.
  54. aliens.empty()
  55. bullets.empty()
  56. # Create a new fleet and center the ship.
  57. create_fleet(ai_settings, screen, ship, aliens)
  58. ship.center_ship()
  59. def fire_bullet(ai_settings, screen, ship, bullets):
  60. """Fire a bullet, if limit not reached yet."""
  61. # Create a new bullet, add to bullets group.
  62. if len(bullets) < ai_settings.bullets_allowed:
  63. new_bullet = Bullet(ai_settings, screen, ship)
  64. bullets.add(new_bullet)
  65. def update_screen(ai_settings, screen, stats, sb, ship, aliens, bullets,
  66. play_button):
  67. """Update images on the screen, and flip to the new screen."""
  68. # Redraw the screen, each pass through the loop.
  69. screen.fill(ai_settings.bg_color)
  70. # Redraw all bullets, behind ship and aliens.
  71. for bullet in bullets.sprites():
  72. bullet.draw_bullet()
  73. ship.blitme()
  74. aliens.draw(screen)
  75. # Draw the score information.
  76. sb.show_score()
  77. # Draw the play button if the game is inactive.
  78. if not stats.game_active:
  79. play_button.draw_button()
  80. # Make the most recently drawn screen visible.
  81. pygame.display.flip()
  82. def update_bullets(ai_settings, screen, stats, sb, ship, aliens, bullets):
  83. """Update position of bullets, and get rid of old bullets."""
  84. # Update bullet positions.
  85. bullets.update()
  86. # Get rid of bullets that have disappeared.
  87. for bullet in bullets.copy():
  88. if bullet.rect.bottom <= 0:
  89. bullets.remove(bullet)
  90. check_bullet_alien_collisions(ai_settings, screen, stats, sb, ship,
  91. aliens, bullets)
  92. def check_high_score(stats, sb):
  93. """Check to see if there's a new high score."""
  94. if stats.score > stats.high_score:
  95. stats.high_score = stats.score
  96. sb.prep_high_score()
  97. def check_bullet_alien_collisions(ai_settings, screen, stats, sb, ship,
  98. aliens, bullets):
  99. """Respond to bullet-alien collisions."""
  100. # Remove any bullets and aliens that have collided.
  101. collisions = pygame.sprite.groupcollide(bullets, aliens, True, True)
  102. if collisions:
  103. for aliens in collisions.values():
  104. stats.score += ai_settings.alien_points * len(aliens)
  105. sb.prep_score()
  106. check_high_score(stats, sb)
  107. if len(aliens) == 0:
  108. # If the entire fleet is destroyed, start a new level.
  109. bullets.empty()
  110. ai_settings.increase_speed()
  111. # Increase level.
  112. stats.level += 1
  113. sb.prep_level()
  114. create_fleet(ai_settings, screen, ship, aliens)
  115. def check_fleet_edges(ai_settings, aliens):
  116. """Respond appropriately if any aliens have reached an edge."""
  117. for alien in aliens.sprites():
  118. if alien.check_edges():
  119. change_fleet_direction(ai_settings, aliens)
  120. break
  121. def change_fleet_direction(ai_settings, aliens):
  122. """Drop the entire fleet, and change the fleet's direction."""
  123. for alien in aliens.sprites():
  124. alien.rect.y += ai_settings.fleet_drop_speed
  125. ai_settings.fleet_direction *= -1
  126. def ship_hit(ai_settings, screen, stats, sb, ship, aliens, bullets):
  127. """Respond to ship being hit by alien."""
  128. if stats.ships_left > 0:
  129. # Decrement ships_left.
  130. stats.ships_left -= 1
  131. # Update scoreboard.
  132. sb.prep_ships()
  133. else:
  134. stats.game_active = False
  135. pygame.mouse.set_visible(True)
  136. # Empty the list of aliens and bullets.
  137. aliens.empty()
  138. bullets.empty()
  139. # Create a new fleet, and center the ship.
  140. create_fleet(ai_settings, screen, ship, aliens)
  141. ship.center_ship()
  142. # Pause.
  143. sleep(0.5)
  144. def check_aliens_bottom(ai_settings, screen, stats, sb, ship, aliens,
  145. bullets):
  146. """Check if any aliens have reached the bottom of the screen."""
  147. screen_rect = screen.get_rect()
  148. for alien in aliens.sprites():
  149. if alien.rect.bottom >= screen_rect.bottom:
  150. # Treat this the same as if the ship got hit.
  151. ship_hit(ai_settings, screen, stats, sb, ship, aliens, bullets)
  152. break
  153. def update_aliens(ai_settings, screen, stats, sb, ship, aliens, bullets):
  154. """
  155. Check if the fleet is at an edge,
  156. then update the postions of all aliens in the fleet.
  157. """
  158. check_fleet_edges(ai_settings, aliens)
  159. aliens.update()
  160. # Look for alien-ship collisions.
  161. if pygame.sprite.spritecollideany(ship, aliens):
  162. ship_hit(ai_settings, screen, stats, sb, ship, aliens, bullets)
  163. # Look for aliens hitting the bottom of the screen.
  164. check_aliens_bottom(ai_settings, screen, stats, sb, ship, aliens, bullets)
  165. def get_number_aliens_x(ai_settings, alien_width):
  166. """Determine the number of aliens that fit in a row."""
  167. available_space_x = ai_settings.screen_width - 2 * alien_width
  168. number_aliens_x = int(available_space_x / (2 * alien_width))
  169. return number_aliens_x
  170. def get_number_rows(ai_settings, ship_height, alien_height):
  171. """Determine the number of rows of aliens that fit on the screen."""
  172. available_space_y = (ai_settings.screen_height -
  173. (3 * alien_height) - ship_height)
  174. number_rows = int(available_space_y / (2 * alien_height))
  175. return number_rows
  176. def create_alien(ai_settings, screen, aliens, alien_number, row_number):
  177. """Create an alien, and place it in the row."""
  178. alien = Alien(ai_settings, screen)
  179. alien_width = alien.rect.width
  180. alien.x = alien_width + 2 * alien_width * alien_number
  181. alien.rect.x = alien.x
  182. alien.rect.y = alien.rect.height + 2 * alien.rect.height * row_number
  183. aliens.add(alien)
  184. def create_fleet(ai_settings, screen, ship, aliens):
  185. """Create a full fleet of aliens."""
  186. # Create an alien, and find number of aliens in a row.
  187. alien = Alien(ai_settings, screen)
  188. number_aliens_x = get_number_aliens_x(ai_settings, alien.rect.width)
  189. number_rows = get_number_rows(ai_settings, ship.rect.height,
  190. alien.rect.height)
  191. # Create the fleet of aliens.
  192. for row_number in range(number_rows):
  193. for alien_number in range(number_aliens_x):
  194. create_alien(ai_settings, screen, aliens, alien_number,
  195. row_number)