10.17: Drawing the Map
- Page ID
- 14678
\( \newcommand{\vecs}[1]{\overset { \scriptstyle \rightharpoonup} {\mathbf{#1}} } \)
\( \newcommand{\vecd}[1]{\overset{-\!-\!\rightharpoonup}{\vphantom{a}\smash {#1}}} \)
\( \newcommand{\id}{\mathrm{id}}\) \( \newcommand{\Span}{\mathrm{span}}\)
( \newcommand{\kernel}{\mathrm{null}\,}\) \( \newcommand{\range}{\mathrm{range}\,}\)
\( \newcommand{\RealPart}{\mathrm{Re}}\) \( \newcommand{\ImaginaryPart}{\mathrm{Im}}\)
\( \newcommand{\Argument}{\mathrm{Arg}}\) \( \newcommand{\norm}[1]{\| #1 \|}\)
\( \newcommand{\inner}[2]{\langle #1, #2 \rangle}\)
\( \newcommand{\Span}{\mathrm{span}}\)
\( \newcommand{\id}{\mathrm{id}}\)
\( \newcommand{\Span}{\mathrm{span}}\)
\( \newcommand{\kernel}{\mathrm{null}\,}\)
\( \newcommand{\range}{\mathrm{range}\,}\)
\( \newcommand{\RealPart}{\mathrm{Re}}\)
\( \newcommand{\ImaginaryPart}{\mathrm{Im}}\)
\( \newcommand{\Argument}{\mathrm{Arg}}\)
\( \newcommand{\norm}[1]{\| #1 \|}\)
\( \newcommand{\inner}[2]{\langle #1, #2 \rangle}\)
\( \newcommand{\Span}{\mathrm{span}}\) \( \newcommand{\AA}{\unicode[.8,0]{x212B}}\)
\( \newcommand{\vectorA}[1]{\vec{#1}} % arrow\)
\( \newcommand{\vectorAt}[1]{\vec{\text{#1}}} % arrow\)
\( \newcommand{\vectorB}[1]{\overset { \scriptstyle \rightharpoonup} {\mathbf{#1}} } \)
\( \newcommand{\vectorC}[1]{\textbf{#1}} \)
\( \newcommand{\vectorD}[1]{\overrightarrow{#1}} \)
\( \newcommand{\vectorDt}[1]{\overrightarrow{\text{#1}}} \)
\( \newcommand{\vectE}[1]{\overset{-\!-\!\rightharpoonup}{\vphantom{a}\smash{\mathbf {#1}}}} \)
\( \newcommand{\vecs}[1]{\overset { \scriptstyle \rightharpoonup} {\mathbf{#1}} } \)
\( \newcommand{\vecd}[1]{\overset{-\!-\!\rightharpoonup}{\vphantom{a}\smash {#1}}} \)
\(\newcommand{\avec}{\mathbf a}\) \(\newcommand{\bvec}{\mathbf b}\) \(\newcommand{\cvec}{\mathbf c}\) \(\newcommand{\dvec}{\mathbf d}\) \(\newcommand{\dtil}{\widetilde{\mathbf d}}\) \(\newcommand{\evec}{\mathbf e}\) \(\newcommand{\fvec}{\mathbf f}\) \(\newcommand{\nvec}{\mathbf n}\) \(\newcommand{\pvec}{\mathbf p}\) \(\newcommand{\qvec}{\mathbf q}\) \(\newcommand{\svec}{\mathbf s}\) \(\newcommand{\tvec}{\mathbf t}\) \(\newcommand{\uvec}{\mathbf u}\) \(\newcommand{\vvec}{\mathbf v}\) \(\newcommand{\wvec}{\mathbf w}\) \(\newcommand{\xvec}{\mathbf x}\) \(\newcommand{\yvec}{\mathbf y}\) \(\newcommand{\zvec}{\mathbf z}\) \(\newcommand{\rvec}{\mathbf r}\) \(\newcommand{\mvec}{\mathbf m}\) \(\newcommand{\zerovec}{\mathbf 0}\) \(\newcommand{\onevec}{\mathbf 1}\) \(\newcommand{\real}{\mathbb R}\) \(\newcommand{\twovec}[2]{\left[\begin{array}{r}#1 \\ #2 \end{array}\right]}\) \(\newcommand{\ctwovec}[2]{\left[\begin{array}{c}#1 \\ #2 \end{array}\right]}\) \(\newcommand{\threevec}[3]{\left[\begin{array}{r}#1 \\ #2 \\ #3 \end{array}\right]}\) \(\newcommand{\cthreevec}[3]{\left[\begin{array}{c}#1 \\ #2 \\ #3 \end{array}\right]}\) \(\newcommand{\fourvec}[4]{\left[\begin{array}{r}#1 \\ #2 \\ #3 \\ #4 \end{array}\right]}\) \(\newcommand{\cfourvec}[4]{\left[\begin{array}{c}#1 \\ #2 \\ #3 \\ #4 \end{array}\right]}\) \(\newcommand{\fivevec}[5]{\left[\begin{array}{r}#1 \\ #2 \\ #3 \\ #4 \\ #5 \\ \end{array}\right]}\) \(\newcommand{\cfivevec}[5]{\left[\begin{array}{c}#1 \\ #2 \\ #3 \\ #4 \\ #5 \\ \end{array}\right]}\) \(\newcommand{\mattwo}[4]{\left[\begin{array}{rr}#1 \amp #2 \\ #3 \amp #4 \\ \end{array}\right]}\) \(\newcommand{\laspan}[1]{\text{Span}\{#1\}}\) \(\newcommand{\bcal}{\cal B}\) \(\newcommand{\ccal}{\cal C}\) \(\newcommand{\scal}{\cal S}\) \(\newcommand{\wcal}{\cal W}\) \(\newcommand{\ecal}{\cal E}\) \(\newcommand{\coords}[2]{\left\{#1\right\}_{#2}}\) \(\newcommand{\gray}[1]{\color{gray}{#1}}\) \(\newcommand{\lgray}[1]{\color{lightgray}{#1}}\) \(\newcommand{\rank}{\operatorname{rank}}\) \(\newcommand{\row}{\text{Row}}\) \(\newcommand{\col}{\text{Col}}\) \(\renewcommand{\row}{\text{Row}}\) \(\newcommand{\nul}{\text{Nul}}\) \(\newcommand{\var}{\text{Var}}\) \(\newcommand{\corr}{\text{corr}}\) \(\newcommand{\len}[1]{\left|#1\right|}\) \(\newcommand{\bbar}{\overline{\bvec}}\) \(\newcommand{\bhat}{\widehat{\bvec}}\) \(\newcommand{\bperp}{\bvec^\perp}\) \(\newcommand{\xhat}{\widehat{\xvec}}\) \(\newcommand{\vhat}{\widehat{\vvec}}\) \(\newcommand{\uhat}{\widehat{\uvec}}\) \(\newcommand{\what}{\widehat{\wvec}}\) \(\newcommand{\Sighat}{\widehat{\Sigma}}\) \(\newcommand{\lt}{<}\) \(\newcommand{\gt}{>}\) \(\newcommand{\amp}{&}\) \(\definecolor{fillinmathshade}{gray}{0.9}\)def drawMap(mapObj, gameStateObj, goals): """Draws the map to a Surface object, including the player and stars. This function does not call pygame.display.update(), nor does it draw the "Level" and "Steps" text in the corner.""" # mapSurf will be the single Surface object that the tiles are drawn # on, so that it is easy to position the entire map on the DISPLAYSURF # Surface object. First, the width and height must be calculated. mapSurfWidth = len(mapObj) * TILEWIDTH mapSurfHeight = (len(mapObj[0]) - 1) * TILEFLOORHEIGHT + TILEHEIGHT mapSurf = pygame.Surface((mapSurfWidth, mapSurfHeight)) mapSurf.fill(BGCOLOR) # start with a blank color on the surface. # Draw the tile sprites onto this surface. for x in range(len(mapObj)): for y in range(len(mapObj[x])): spaceRect = pygame.Rect((x * TILEWIDTH, y * TILEFLOORHEIGHT, TILEWIDTH, TILEHEIGHT)) if mapObj[x][y] in TILEMAPPING: baseTile = TILEMAPPING[mapObj[x][y]] elif mapObj[x][y] in OUTSIDEDECOMAPPING: baseTile = TILEMAPPING[' '] # First draw the base ground/wall tile. mapSurf.blit(baseTile, spaceRect) if mapObj[x][y] in OUTSIDEDECOMAPPING: # Draw any tree/rock decorations that are on this tile. mapSurf.blit(OUTSIDEDECOMAPPING[mapObj[x][y]], spaceRect) elif (x, y) in gameStateObj['stars']: if (x, y) in goals: # A goal AND star are on this space, draw goal first. mapSurf.blit(IMAGESDICT['covered goal'], spaceRect) # Then draw the star sprite. mapSurf.blit(IMAGESDICT['star'], spaceRect) elif (x, y) in goals: # Draw a goal without a star on it. mapSurf.blit(IMAGESDICT['uncovered goal'], spaceRect) # Last draw the player on the board. if (x, y) == gameStateObj['player']: # Note: The value "currentImage" refers # to a key in "PLAYERIMAGES" which has the # specific player image we want to show. mapSurf.blit(PLAYERIMAGES[currentImage], spaceRect) return mapSurf
The drawMap()
function will return a Surface object with the entire map (and the player and stars) drawn on it. The width and height needed for this Surface have to be calculated from mapObj
(which is done on line 9 [543] and 10 [544]). The Surface object that everything will be drawn on is created on line 11 [545]. To begin with, the entire Surface object is painted to the background color on line 12 [546].
The set of nested for
loops on line 15 [549] and 16 [550] will go through every possible XY coordinate on the map and draw the appropriate tile image at that location.
The baseTile
variable is set to the Surface object of the tile image to be drawn at the iteration’s current XY coordinate. If the single-character string is in the OUTSIDEDECOMAPPING
dictionary, then TILEMAPPING[' ']
(the single-character string for the basic outdoor floor tile) will be used.
Additionally, if the tile was listed in the OUTSIDEDECOMAPPING
dictionary, the corresponding tree or rock image should be drawn on top of the tile that was just drawn at that XY coordinate.
If there is a star located at this XY coordinate on the map (which can be found out by checking for (x, y)
in the list at gameStateObj['stars'])
, then a star should be drawn at this XY coordinate (which is done on line 34 [568]). Before the star is drawn, the code should first check if there is also a goal at this location, in which case, the "covered goal" tile should be drawn first.
If there is a goal at this XY coordinate on the map, then the "uncovered goal" should be drawn on top of the tile. The uncovered goal is drawn because if execution has reached the elif
statement on line 35 [569], we know that the elif
statement’s condition on line 29 [563] was False
and there is no star that is also at this XY coordinate.
Finally, the drawMap()
function checks if the player is located at this XY coordinate, and if so, the player’s image is drawn over the tile. Line 46 [580] is outside of the nested for loops that began on line 15 [549] and 16 [550], so by the time the Surface object is returned, the entire map has been drawn on it.