all repos — Legends-RPG @ ad405fd726359ea8a62b0a89eb8333c5ff562d76

A fantasy mini-RPG built with Python and Pygame.

data/tilemap.py (view raw)

  1__author__ = 'justinarmstrong'
  2
  3import os
  4import pygame as pg
  5from . import tools, setup
  6from . components import person, portal
  7from . import constants as c
  8
  9
 10def create_town_sprite_sheet_dict():
 11    """Create a dictionary of sprite sheet tiles"""
 12    tile_dict = {}
 13    tileset1 = setup.GFX['tileset1']
 14    tileset2 = setup.GFX['tileset2']
 15    tileset3 = setup.GFX['tileset3']
 16    shopsigns = setup.GFX['shopsigns']
 17    castle_door = setup.GFX['castledoor']
 18    medieval_signs = setup.GFX['medievalsigns']
 19    house = setup.GFX['house']
 20    houseoverworld = setup.GFX['houseoverworld']
 21
 22    tile_dict['pavement'] = get_tile(32, 48, tileset2)
 23    tile_dict['house wall'] = get_tile(64, 48, tileset2)
 24    tile_dict['house roof'] = get_tile(0, 144, tileset2)
 25    tile_dict['house door'] = get_tile(48, 64, tileset2)
 26    tile_dict['tree'] = get_tile(80, 48, tileset1, 16, 32)
 27    tile_dict['well'] = get_tile(96, 50, tileset1, 16, 32)
 28    tile_dict['moat'] = get_tile(16, 16, tileset2)
 29    tile_dict['fence'] = get_tile(48, 64, tileset1)
 30    tile_dict['grass'] = get_tile(0, 16, tileset1)
 31    tile_dict['sword'] = get_tile(96, 0, shopsigns, 32, 32)
 32    tile_dict['shield'] = get_tile(64, 0, shopsigns, 32, 32)
 33    tile_dict['potion'] = get_tile(32, 0, shopsigns, 32, 32)
 34    tile_dict['gem'] = get_tile(0, 0, shopsigns, 32, 32)
 35    tile_dict['castle bridge'] = get_tile(48, 27, tileset1, 16, 32 )
 36    tile_dict['flower1'] = get_tile(64, 64, tileset2)
 37    tile_dict['flower2'] = get_tile(80, 64, tileset2)
 38    tile_dict['horiz castle wall'] = get_tile(32, 0, tileset3, 48, 32)
 39    tile_dict['left vert castle wall'] = get_tile(0, 16, tileset3)
 40    tile_dict['right vert castle wall'] = get_tile(162, 16, tileset3)
 41    tile_dict['castle tower'] = get_tile(116, 16, tileset1, 48, 64)
 42    tile_dict['main castle roof'] = get_tile(0, 0, tileset1, 160, 16)
 43    tile_dict['left castle roof piece'] = get_tile(0, 0, tileset1, 48, 16)
 44    tile_dict['right castle roof piece'] = get_tile(112, 0, tileset1, 48, 16)
 45    tile_dict['castle side'] = get_tile(0, 72, tileset3)
 46    tile_dict['castle door'] = get_tile(0, 0, castle_door, 64, 96)
 47    tile_dict['carpet topleft'] = get_tile(112, 112, tileset2)
 48    tile_dict['carpet topright'] = get_tile(144, 112, tileset2)
 49    tile_dict['carpet bottomleft'] = get_tile(112, 144, tileset2)
 50    tile_dict['carpet bottomright'] = get_tile(144, 144, tileset2)
 51    tile_dict['carpet bottom'] = get_tile(128, 144, tileset2)
 52    tile_dict['carpet top'] = get_tile(128, 112, tileset2)
 53    tile_dict['carpet left'] = get_tile(112, 128, tileset2)
 54    tile_dict['carpet right'] = get_tile(144, 128, tileset2)
 55    tile_dict['carpet center'] = get_tile(128, 128, tileset2)
 56    tile_dict['castle window'] = get_tile(128, 59, tileset1)
 57    tile_dict['marble floor'] = get_tile(80, 96, tileset3)
 58    tile_dict['inn sign'] = get_tile(0, 96, medieval_signs, 32, 32)
 59    tile_dict['banner1'] = get_tile(112, 38, tileset3, 16, 22)
 60    tile_dict['banner2'] = get_tile(128, 38, tileset3, 16, 22)
 61    tile_dict['banner3'] = get_tile(144, 38, tileset3, 16, 22)
 62    tile_dict['black tile'] = make_black_surface_tile()
 63    tile_dict['bed'] = get_tile(456, 206, house, 48, 82)
 64    tile_dict['shelves'] = get_tile(352, 116, house, 160, 70)
 65    tile_dict['chair'] = get_tile(323, 256, house, 32, 32)
 66    tile_dict['table'] = get_tile(82, 161, tileset3, 46, 32)
 67    tile_dict['fancy carpet'] = get_tile(112, 96, tileset3, 64, 64)
 68    tile_dict['column'] = get_tile(64, 96, tileset3, 16, 48)
 69    tile_dict['bottomwater1'] = get_tile(16, 32, tileset2)
 70    tile_dict['bottomwater2'] = get_tile(32, 32, tileset2)
 71    tile_dict['bottomwater3'] = get_tile(48, 32, tileset2)
 72    tile_dict['topwater1'] = get_tile(16, 0, tileset2)
 73    tile_dict['topwater2'] = get_tile(32, 0, tileset2)
 74    tile_dict['topwater3'] = get_tile(48, 0, tileset2)
 75    tile_dict['leftwater1'] = get_tile(80, 0, tileset2)
 76    tile_dict['leftwater2'] = get_tile(80, 16, tileset2)
 77    tile_dict['leftwater3'] = get_tile(0, 16, tileset2)
 78    tile_dict['rightwater1'] = get_tile(144, 0, tileset2)
 79    tile_dict['rightwater2'] = get_tile(144, 16, tileset2)
 80    tile_dict['rightwater3'] = get_tile(64, 16, tileset2)
 81    tile_dict['houseoverworld'] = get_tile(0, 0, houseoverworld, 128, 128)
 82
 83    return tile_dict
 84
 85def create_layer1_tile_code_dict():
 86    """Creates a dictionary of codes to tiles for layer 1"""
 87    tile_dict = {'1': 'pavement',
 88                 '2': 'house wall',
 89                 '3': 'house roof',
 90                 'T': 'tree',
 91                 'W': 'well',
 92                 'M': 'moat',
 93                 'G': 'grass',
 94                 'B': 'castle bridge',
 95                 'V': 'left vert castle wall',
 96                 'C': 'horiz castle wall',
 97                 'X': 'right vert castle wall',
 98                 'S': 'castle side',
 99                 'Q': 'carpet topleft',
100                 'E': 'carpet topright',
101                 'J': 'carpet top',
102                 'R': 'carpet bottomleft',
103                 'U': 'carpet bottomright',
104                 'D': 'carpet bottom',
105                 'P': 'carpet left',
106                 'A': 'carpet right',
107                 'F': 'carpet center',
108                 'H': 'marble floor',
109                 'K': 'black tile',
110                 'L': 'topwater1',
111                 'N': 'topwater2',
112                 'Y': 'topwater3',
113                 'Z': 'leftwater1',
114                 '4': 'leftwater2',
115                 '5': 'leftwater3',
116                 '6': 'rightwater1',
117                 '7': 'rightwater2',
118                 '8': 'rightwater3',
119                 '9': 'bottomwater1',
120                 'a': 'bottomwater2',
121                 'b': 'bottomwater3'
122                }
123
124    return tile_dict
125
126
127def get_tile(x, y, tileset, width=16, height=16, scale=1):
128    """Gets the surface and rect for a tile"""
129    surface = get_image(x, y, width, height, tileset)
130    surface = pg.transform.scale(surface, (int(width*scale), int(height*scale)))
131    rect = surface.get_rect()
132
133    tile_dict = {'surface': surface,
134                 'rect': rect}
135
136    return tile_dict
137
138
139def make_black_surface_tile():
140    """Make a black surface"""
141    surface = pg.Surface((32, 32))
142    surface.fill(c.NEAR_BLACK_BLUE)
143    rect = surface.get_rect()
144    new_dict = {'surface': surface,
145                'rect': rect}
146
147    return new_dict
148
149
150def make_background(state_name, width, height):
151    """Creates the background surface that the rest of
152    the town map will be blitted on"""
153    size = (width*16, height*16)
154    surface = pg.Surface(size)
155    if state_name == c.TOWN or state_name == c.OVERWORLD:
156        tile = get_image(0, 0, 16, 16, setup.GFX['tileset2'])
157    else:
158        tile = pg.Surface((16, 16))
159        tile.fill(c.BLACK_BLUE)
160
161    rect = tile.get_rect()
162
163    for row in range(height):
164        for column in range(width):
165            rect.y = row * 16
166            rect.x = column * 16
167            surface.blit(tile, rect)
168
169    return surface
170
171
172def create_map_layer1(state, width, height):
173    """Creates the town from a tile map and creates a
174    surface on top of the background"""
175    map = make_background(state, width, height)
176
177    tile_map = open(os.path.join('data', 'states', state, 'layer1.txt'), 'r')
178
179    for row, line in enumerate(tile_map):
180        for column, letter in enumerate(line):
181            if letter not in layer1_tile_code_dict:
182                pass
183            else:
184                tile = tile_dict[layer1_tile_code_dict[letter]]
185                blit_tile_to_map(tile, row, column, map)
186
187    tile_map.close()
188
189    layer1_extra = create_map_layer2(state, width, height, 'layer1extra.txt')
190    map.blit(layer1_extra, (0,0))
191
192    map = scale_map(map)
193
194    return map
195
196
197def create_map_layer2(state, width, height, file_name='layer2.txt'):
198    """Creates doors and other items on top of the rest of the map"""
199    map = make_background(None, width, height)
200    map.set_colorkey(c.BLACK_BLUE)
201
202    tile_map = open(os.path.join('data', 'states', state, file_name), 'r')
203
204    for row, line in enumerate(tile_map):
205        for column, letter in enumerate(line):
206            if letter == 'D':
207                tile = tile_dict['house door']
208                blit_tile_to_map(tile, row, column, map)
209            elif letter == 'F':
210                tile = tile_dict['fence']
211                blit_tile_to_map(tile, row, column, map)
212            elif letter == '$':
213                tile = tile_dict['flower1']
214                blit_tile_to_map(tile, row, column, map)
215            elif letter == '*':
216                tile = tile_dict['flower2']
217                blit_tile_to_map(tile, row, column, map)
218            elif letter == 'T':
219                tile = tile_dict['castle tower']
220                blit_tile_to_map(tile, row, column, map)
221            elif letter == 'W':
222                tile = tile_dict['left vert castle wall']
223                blit_tile_to_map(tile, row, column, map)
224            elif letter == 'M':
225                tile = tile_dict['main castle roof']
226                blit_tile_to_map(tile, row, column, map)
227            elif letter == 'L':
228                tile = tile_dict['left castle roof piece']
229                blit_tile_to_map(tile, row, column, map)
230            elif letter == 'R':
231                tile = tile_dict['right castle roof piece']
232                blit_tile_to_map(tile, row, column, map)
233            elif letter == '#':
234                tile = tile_dict['tree']
235                blit_tile_to_map(tile, row, column, map)
236            elif letter == 'O':
237                tile = tile_dict['castle door']
238                blit_tile_to_map(tile, row, column, map)
239            elif letter == 'Q':
240                tile = tile_dict['castle window']
241                blit_tile_to_map(tile, row, column, map)
242            elif letter == 'A':
243                tile = tile_dict['banner1']
244                blit_tile_to_map(tile, row, column, map)
245            elif letter == 'B':
246                tile = tile_dict['banner2']
247                blit_tile_to_map(tile, row, column, map)
248            elif letter == 'C':
249                tile = tile_dict['banner3']
250                blit_tile_to_map(tile, row, column, map)
251            elif letter == 'E':
252                tile = tile_dict['bed']
253                blit_tile_to_map(tile, row, column, map)
254            elif letter == 'G':
255                tile = tile_dict['shelves']
256                blit_tile_to_map(tile, row, column, map)
257            elif letter == 'H':
258                tile = tile_dict['chair']
259                blit_tile_to_map(tile, row, column, map)
260            elif letter == 'I':
261                tile = tile_dict['table']
262                blit_tile_to_map(tile, row, column, map)
263            elif letter == 'J':
264                tile = tile_dict['fancy carpet']
265                blit_tile_to_map(tile, row, column, map)
266            elif letter == 'K':
267                tile = tile_dict['column']
268                blit_tile_to_map(tile, row, column, map)
269            elif letter == 'N':
270                tile = tile_dict['black tile']
271                blit_tile_to_map(tile, row, column, map)
272            elif letter == 'P':
273                tile = tile_dict['houseoverworld']
274                blit_tile_to_map(tile, row, column, map)
275
276    tile_map.close()
277
278    if file_name == 'layer2.txt':
279        map = pg.transform.scale2x(map)
280        map = create_map_layer3(map, state)
281
282    return map
283
284
285def scale_map(map):
286    """Double resolution of map to 32x32"""
287    map = pg.transform.scale2x(map)
288
289    return map
290
291
292def create_map_layer3(map, state):
293    """Layers for images that are already 32x32"""
294    tile_map = open(os.path.join('data', 'states', state, 'layer3.txt'), 'r')
295
296    for row, line in enumerate(tile_map):
297        for column, letter in enumerate(line):
298            if letter == 'W':
299                tile = tile_dict['sword']
300                blit_tile_to_map(tile, row, column, map, 32)
301            elif letter == 'A':
302                tile = tile_dict['shield']
303                blit_tile_to_map(tile, row, column, map, 32)
304            elif letter == 'P':
305                tile = tile_dict['potion']
306                blit_tile_to_map(tile, row, column, map, 32)
307            elif letter == 'M':
308                tile = tile_dict['gem']
309                blit_tile_to_map(tile, row, column, map, 32)
310            elif letter == 'I':
311                tile = tile_dict['inn sign']
312                blit_tile_to_map(tile, row, column, map, 32)
313            elif letter == 'B':
314                tile = tile_dict['chair']
315                blit_tile_to_map(tile, row, column, map, 32)
316
317
318    tile_map.close()
319
320    return map
321
322
323
324def blit_tile_to_map(tile, row, column, map, side_length=16):
325    """Places tile to map"""
326    tile['rect'].x = column * side_length
327    tile['rect'].y = row * side_length
328
329    map.blit(tile['surface'], tile['rect'])
330
331
332def create_blockers(state):
333    """Creates invisible rect objects that will prevent the player from
334    walking into trees, buildings and other solid objects"""
335    tile_map = open(os.path.join('data', 'states', state, 'blockers.txt'), 'r')
336    blockers = []
337
338    for row, line in enumerate(tile_map):
339        for column, letter in enumerate(line):
340            if letter == 'B':
341                blockers.append(pg.Rect(column*32, row*32, 32, 32))
342
343    tile_map.close()
344
345    return blockers
346
347
348def make_level_surface(map):
349    """Creates the surface all images are blitted to"""
350    map_rect = map.get_rect()
351    size = map_rect.size
352
353
354    return pg.Surface(size).convert()
355
356
357def create_viewport(map):
358    """Create the viewport to view the level through"""
359    map_rect = map.get_rect()
360    return setup.SCREEN.get_rect(bottom=map_rect.bottom)
361
362
363def set_sprite_positions(player, level_sprites, state, game_data):
364    """Set the start positions for all the sprites in the level"""
365    start_pos_key = state + ' start pos'
366    x =  game_data[start_pos_key][0]*32
367    y = game_data[start_pos_key][1]*32
368    player.rect = pg.Rect(x, y, 32, 32)
369
370    tile_map = open(os.path.join('data', 'states', state, 'sprite_start_pos.txt'), 'r')
371
372    for row, line in enumerate(tile_map):
373        for column, letter in enumerate(line):
374            if letter == 'F':
375                fem_villager = person.FemaleVillager(column*32, row*32)
376                level_sprites.add(fem_villager)
377            elif letter == 'S':
378                soldier = person.Soldier(column*32, row*32)
379                level_sprites.add(soldier)
380            elif letter == 'A':
381                soldier = person.Soldier(column*32, row*32, 'right', 'resting')
382                level_sprites.add(soldier)
383            elif letter == 'B':
384                soldier = person.Soldier(column*32, row*32, 'left', 'resting')
385                level_sprites.add(soldier)
386            elif letter == 'C':
387                king = person.King(column*32, row*32, 'down', 'resting')
388                level_sprites.add(king)
389            elif letter == 'D':
390                well = person.Well(column*32, row*32)
391                level_sprites.add(well)
392            elif letter == 'E':
393                fem_villager = person.FemaleVillager2(column*32, row*32)
394                level_sprites.add(fem_villager)
395            elif letter == 'G':
396                devil_villager = person.Devil(column*32, row*32)
397                level_sprites.add(devil_villager)
398            elif letter == 'H':
399                old_villager = person.OldMan(column*32, row*32)
400                level_sprites.add(old_villager)
401
402    tile_map.close()
403
404
405def make_level_portals(state):
406    """Create portals to different levels on doors"""
407    tile_map = open(os.path.join('data', 'states', state, 'portals.txt'), 'r')
408    portal_group = pg.sprite.Group()
409
410    for row, line in enumerate(tile_map):
411        for column, letter in enumerate(line):
412            if letter == 'A':
413                portal_group.add(portal.Portal(column, row, c.CASTLE))
414            elif letter == 'B':
415                portal_group.add(portal.Portal(column, row, c.TOWN))
416            elif letter == 'C':
417                portal_group.add(portal.Portal(column, row, c.INN))
418            elif letter == 'D':
419                portal_group.add(portal.Portal(column, row, c.MAGIC_SHOP))
420            elif letter == 'E':
421                portal_group.add(portal.Portal(column, row, c.POTION_SHOP))
422            elif letter == 'F':
423                portal_group.add(portal.Portal(column, row, c.WEAPON_SHOP))
424            elif letter == 'G':
425                portal_group.add(portal.Portal(column, row, c.ARMOR_SHOP))
426            elif letter == 'H':
427                portal_group.add(portal.Portal(column, row, c.HOUSE))
428            elif letter == 'J':
429                portal_group.add(portal.Portal(column, row, c.OVERWORLD))
430
431    return portal_group
432
433
434
435get_image = tools.get_image
436tile_dict = create_town_sprite_sheet_dict()
437layer1_tile_code_dict = create_layer1_tile_code_dict()
438