第13步-更多类型的层#
对于这个例子,我们将切换到一个不同的内置地图,它有更多的层可以用来做事情。
在我们的设置功能中,加载此地图,而不是第12章中的地图:
self.tile_map = arcade.load_tilemap(":resources:tiled_maps/map2_level_1.json", scaling=TILE_SCALING, layer_options=layer_options)
您可以运行此程序并查看我们将在本章中使用的地图。你会注意到,除了我们已经拥有的正常平台和硬币之外。我们现在有了一些额外的标志和装饰物品,以及一个熔岩坑。
回到第6章,我们利用我们的 setup
重置游戏的功能。让我们继续使用这个系统,当玩家接触到熔岩坑时,重新设置游戏。如果需要,您可以在按Esc键时删除用于重置的部分,也可以将其保留在原处。当这种情况发生时,我们也可以通过声音玩游戏。
让我们首先为我们的 __init__
函数用于以下操作:
self.gameover_sound = arcade.load_sound(":resources:sounds/gameover1.wav")
为了做到这一点,我们将在我们的 on_update
功能:
if arcade.check_for_collision_with_list(
self.player_sprite, self.scene["Don't Touch"]
):
arcade.play_sound(self.gameover_sound)
self.setup()
我们在这里使用的地图中有一些额外的层,我们还没有使用过。在上面的代码中,我们使用 Don't Touch
在玩家触摸游戏时重置游戏。在这一部分中,我们将使用新地图中的另外两个图层, Background
和 Foreground
。
我们将使用这些层来区分应该在玩家面前绘制的对象和应该在玩家后面绘制的对象。在我们的 setup
函数,在我们创建PlayerSprite之前,添加以下代码。
self.scene.add_sprite_list_after("Player", "Foreground")
这段代码将使我们的玩家精灵列表被插入到场景中的特定位置。使它前面的精灵画在它前面,后面的精灵画在后面。通过这样做,我们可以使对象出现在玩家的前面或后面,如下图所示:


源代码#
更多层#
1"""
2Platformer Game
3
4python -m arcade.examples.platform_tutorial.13_more_layers
5"""
6import arcade
7
8# Constants
9SCREEN_WIDTH = 800
10SCREEN_HEIGHT = 600
11SCREEN_TITLE = "Platformer"
12
13# Constants used to scale our sprites from their original size
14TILE_SCALING = 0.5
15COIN_SCALING = 0.5
16
17# Movement speed of player, in pixels per frame
18PLAYER_MOVEMENT_SPEED = 5
19GRAVITY = 1
20PLAYER_JUMP_SPEED = 20
21
22
23class MyGame(arcade.Window):
24 """
25 Main application class.
26 """
27
28 def __init__(self):
29
30 # Call the parent class and set up the window
31 super().__init__(SCREEN_WIDTH, SCREEN_HEIGHT, SCREEN_TITLE)
32
33 # Variable to hold our texture for our player
34 self.player_texture = None
35
36 # Separate variable that holds the player sprite
37 self.player_sprite = None
38
39 # Variable to hold our Tiled Map
40 self.tile_map = None
41
42 # Replacing all of our SpriteLists with a Scene variable
43 self.scene = None
44
45 # A variable to store our camera object
46 self.camera = None
47
48 # A variable to store our gui camera object
49 self.gui_camera = None
50
51 # This variable will store our score as an integer.
52 self.score = 0
53
54 # This variable will store the text for score that we will draw to the screen.
55 self.score_text = None
56
57 # Load sounds
58 self.collect_coin_sound = arcade.load_sound(":resources:sounds/coin1.wav")
59 self.jump_sound = arcade.load_sound(":resources:sounds/jump1.wav")
60 self.gameover_sound = arcade.load_sound(":resources:sounds/gameover1.wav")
61
62 def setup(self):
63 """Set up the game here. Call this function to restart the game."""
64 layer_options = {
65 "Platforms": {
66 "use_spatial_hash": True
67 }
68 }
69
70 # Load our TileMap
71 self.tile_map = arcade.load_tilemap(":resources:tiled_maps/map2_level_1.json", scaling=TILE_SCALING, layer_options=layer_options)
72
73 # Create our Scene Based on the TileMap
74 self.scene = arcade.Scene.from_tilemap(self.tile_map)
75
76 self.player_texture = arcade.load_texture(":resources:images/animated_characters/female_adventurer/femaleAdventurer_idle.png")
77
78 # Add Player Spritelist before "Foreground" layer. This will make the foreground
79 # be drawn after the player, making it appear to be in front of the Player.
80 # Setting before using scene.add_sprite allows us to define where the SpriteList
81 # will be in the draw order. If we just use add_sprite, it will be appended to the
82 # end of the order.
83 self.scene.add_sprite_list_after("Player", "Foreground")
84
85 self.player_sprite = arcade.Sprite(self.player_texture)
86 self.player_sprite.center_x = 128
87 self.player_sprite.center_y = 128
88 self.scene.add_sprite("Player", self.player_sprite)
89
90 # Create a Platformer Physics Engine, this will handle moving our
91 # player as well as collisions between the player sprite and
92 # whatever SpriteList we specify for the walls.
93 # It is important to supply static to the walls parameter. There is a
94 # platforms parameter that is intended for moving platforms.
95 # If a platform is supposed to move, and is added to the walls list,
96 # it will not be moved.
97 self.physics_engine = arcade.PhysicsEnginePlatformer(
98 self.player_sprite, walls=self.scene["Platforms"], gravity_constant=GRAVITY
99 )
100
101 # Initialize our camera, setting a viewport the size of our window.
102 self.camera = arcade.camera.Camera2D()
103
104 # Initialize our gui camera, initial settings are the same as our world camera.
105 self.gui_camera = arcade.camera.Camera2D()
106
107 # Reset our score to 0
108 self.score = 0
109
110 # Initialize our arcade.Text object for score
111 self.score_text = arcade.Text(f"Score: {self.score}", x=0, y=5)
112
113 self.background_color = arcade.csscolor.CORNFLOWER_BLUE
114
115 def on_draw(self):
116 """Render the screen."""
117
118 # Clear the screen to the background color
119 self.clear()
120
121 # Activate our camera before drawing
122 self.camera.use()
123
124 # Draw our Scene
125 self.scene.draw()
126
127 # Activate our GUI camera
128 self.gui_camera.use()
129
130 # Draw our Score
131 self.score_text.draw()
132
133 def on_update(self, delta_time):
134 """Movement and Game Logic"""
135
136 # Move the player using our physics engine
137 self.physics_engine.update()
138
139 # See if we hit any coins
140 coin_hit_list = arcade.check_for_collision_with_list(
141 self.player_sprite, self.scene["Coins"]
142 )
143
144 # Loop through each coin we hit (if any) and remove it
145 for coin in coin_hit_list:
146 # Remove the coin
147 coin.remove_from_sprite_lists()
148 arcade.play_sound(self.collect_coin_sound)
149 self.score += 75
150 self.score_text.text = f"Score: {self.score}"
151
152 if arcade.check_for_collision_with_list(
153 self.player_sprite, self.scene["Don't Touch"]
154 ):
155 arcade.play_sound(self.gameover_sound)
156 self.setup()
157
158 # Center our camera on the player
159 self.camera.position = self.player_sprite.position
160
161 def on_key_press(self, key, modifiers):
162 """Called whenever a key is pressed."""
163
164 if key == arcade.key.ESCAPE:
165 self.setup()
166
167 if key == arcade.key.UP or key == arcade.key.W:
168 if self.physics_engine.can_jump():
169 self.player_sprite.change_y = PLAYER_JUMP_SPEED
170 arcade.play_sound(self.jump_sound)
171
172 if key == arcade.key.LEFT or key == arcade.key.A:
173 self.player_sprite.change_x = -PLAYER_MOVEMENT_SPEED
174 elif key == arcade.key.RIGHT or key == arcade.key.D:
175 self.player_sprite.change_x = PLAYER_MOVEMENT_SPEED
176
177 def on_key_release(self, key, modifiers):
178 """Called whenever a key is released."""
179
180 if key == arcade.key.LEFT or key == arcade.key.A:
181 self.player_sprite.change_x = 0
182 elif key == arcade.key.RIGHT or key == arcade.key.D:
183 self.player_sprite.change_x = 0
184
185
186def main():
187 """Main function"""
188 window = MyGame()
189 window.setup()
190 arcade.run()
191
192
193if __name__ == "__main__":
194 main()