Python Text RPG
-Map Grid and Movement-
So to get going we need some were for the player to be. A sort of world we can display to the player and keep track of their location. We will need to lay a good bit of ground work for this. But before that Lets go a really simple way as a demo.
- I'll update / finish this post at my earliest opportunity -
Last update: ` 2021/12/20 - 23:47 `
Until then I do encourage you to look at and try out the code in your own project.
SIMPLE DEMO:
_______________________________________________________________
# Setup the player with information about the world and their choices.
print("Welcome to this game of text walls!")
print("You are in an empty room; on the wast wall is a door, on the east wall is a small window.\n")
print("What do you do?")
answer = input(">")
print() # add a new line after the players answer in the console
# A dictionary of the choices and their text pairing.
paths = { "west" : "The door is locked!", "east" : "It's to dark to see anything out the window.", "none" : "you stand still, still as a board." }
# A list is returned from the comprehension comparison. We want the 1st (aka the 0th) element, IF there is anything in the list.
player_action = [ opt for ind, opt in enumerate( paths ) if opt.lower() in answer.lower() or answer == str( ind+1 ) ]
# We want to print out the results of the players choice.
action_result = paths[player_action[0]] if 0 < len( player_action ) else path["none"]
print( action_result )
# Rinse repeat a million times. This concludes the short demo.
# This is the kind of text RPG programming I have found on the web. But not quite what I was looking for. I'm going for a more object oriented and easy to maintain project file. So hopefully this train wreck will be of interest to you.
- END -
_______________________________________________________________
section status: WIP - ` 2021/12/20 - 16:21 `
" W.I.P. Disclaimer: I have yet to test run this code it's just out of my brain so It may not work. "
# On to the kind of Object Oriented Programming! First lets make a class that will handle changing the currently active map.
class Game_Manager():
current_node = None
previous_node = None
def __init__( self, **kewargs ):
current_node = None
previous_node = None
attrs_list = [ p for p in dir(self) if not p.startswith( "_" ) and not callable(getattr( self, p )) ]
catch = [ setattr(self, k, kewargs[k] ) for k in kewargs if k in attrs_list ]
def travel( self, next_node ):
if not next: return self.current_node
self.previous_node = self.current_node
self.current_node = next_node
return self.current_node
travel_manager = Travel_Manager()
_______________________________________________________________
section status: WIP - ` 2021/12/19 - 23:08 `
# This class will handle printing information about maps and the players actions to the console.
class Display_Manger():
# Get a list of places the player can go from the current map; [ "Bar", "shop", "soldiers office" ]
read_travel( self ): pass
# Get a list of actions the player can take. Go, Leave, Inspect, Open
read_options( self ): pass
# Format and print out the gathered information to the console
display( self ): pass
_______________________________________________________________
section status: WIP - ` 2021/12/19 - 22:52 `
class Tile():
xy_pose = ()
walkable = False
contents = []
def __init__( self, xy_pose, walkable ):
self.xy_pose = xy_pose
self.walkable = walkable
self.status()
def __repr__( self ):
return f"{self.xy_pose}, {self.walkable}"
def status( self ):
print( self.__repr__() )
_______________________________________________________________
section status: WIP - ` 2021/12/19 - 23:27 `
class Grid():
height = 10
width = 10
map_grid = [] # The main container for the gird
width = 10
map_grid = [] # The main container for the gird
def __init__( self, width, height ):
# Initialize a flat 10x10 grid of Tile objects
for row in range( 0, height ):
map_grid.append( [] ) # Append an empty 'row' array.
map_grid.append( [] ) # Append an empty 'row' array.
# Create new Tile object for every 'square' in the grid row.
for column in range( 0, width ):
map_grid[row].append( Tile( ( row, column ), True ) )
_______________________________________________________________
section status: WIP - ` 2021/12/20 - 23:47 `
# This one is getting a wee long, I might break it out into a seperate post so I can add commentary on how the class works otuside of the inline comments.
class Location():
location_name = ""simple_tag = ""
sublocations = []
play_grid = None
contents = {
"occupants" : {
"player" : [],
"NPC" : [],
"monster" : []
},
"structure" : [],
"props" : {
"general" : [],
"envy" : [],
"utility" : [],
"media" : [],
"consumable" : [],
"tableware" : [],
"lights" : [],
"appliance" : [],
"furniture" : [],
"drapery" : [],
"containers" : []
}
}
def __init__( self, name, simple_tag, width=0, height=0, contents ):
self.location_name = name.lower()
self.simple_tag = simple_tag.lower()
self.sublocations = []
self.play_grid = Grid( width, height ) if width != 0 and height != 0 else None
self.contents = contents if contents else self.__class__.contents.copy()
def _child_index( self, child ):
return self.sublocations.index( child )
def _sortby_tag( self, tag ): pass
def _search_child_name( self, name ):
out = [ loc for loc in self.sublocations if loc.location_name in name ]
return out[0] if 0 < len( out ) else None
def _search_child_object( self, child ):
if child in self.sublocations or child.location_name in ''.join( f"{self.sublocations}" ):
return child
return None
def _add_child_location( self, newChild ):
if self._search_child_object( newChild ):
return None
self.sublocations.append( newChild )
return newChild, self._child_index( newChild )
def children( self, *children ):
# Sort Lists of Valid Data
return self, [ self._add_child_location( child ) if Location is type( child ) else self._search_child_name( child ) if str is type( child ) else None for child in children ]
def __str__( self ):
return f"{self.location_name, self.simple_tag}"
def __repr__( self ):
return f"{self.location_name, self.simple_tag, str(self.play_grid)}"
vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv
# The general overmap
overmap_setup = Location("overmap", "map")
# The town of Varnum
varnum_setup = Location("Varnum", "zone")
print( overmap_setup.children( varnum_setup ) ) # Add Varnum to the Overmap
# Sites in Varnum
print( varnum_setup.children( Location("the broken kettle", 'bar'), Location("tyvan's quality goods", 'shop') ) )
print( varnum_setup.children( Location("silver heron guild", 'recruitment office') ) )
approuch = varnum_setup.children( Location("town approach", 'battle map', 10, 10) )
print( approuch )
# Duplicate validation
print( f"DUPLICATE - Nothing added to {varnum_setup.location_name}: { varnum_setup.children( Location('silver heron guild', 'recruitment office') ) }" )
# search for a location by name
print( f"NAME SEARCH: { varnum_setup._search_child_name( 'the broken kettle' ) }" )
print( f"NAME SEARCH: { varnum_setup.children( 'the broken kettle') }" )
# End result validation
print( varnum_setup.sublocations )
vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv
# Example of how to use Location in practice:
# please note all variables; (Zone, Subzone, etc.) are all Location objects, just named for clarity.Zone = "Elwynn Forest"
Subzone = ["Goldshire"]
Subzone = "Goldshire"
Site = [ "blacksmith", "inn"]
Site = "inn"
Map = [ "floor_0", "floor_1", "floor_2", "roof"]
Map = "floor_2"
Room = ["room_1"]
Room = "room_1"
# Contents have an { object : ( x_pos, y_pos ) }
Contents = {
"occupants" : {
"player_id" : [ "player_id" ],
"NPC" : ["barkeep", "cook", "barmaid", "wine steward"],
"monster" : ["chicken_1", "rat_1", "rat_2"]
},
"structure" : ["wall", "wall", "wall", "wall", "door_1", "window_1"],
"props" : {
"media" : ["book"],
"consumable" : ["meat on bone"],
"kitchen" : ["bowel_wood", "cup_tin", "bottle_glass_empty"],
"lights" : ["tri_candle_stand"],
"furniture" : ["shoe_wrack", "table", "wardrobe_wood", "chair_wood", "bed_queen", "table_side_wood"],
"drapery" : ["rug_large", "bed_canopy", "shirt_brown"],
"containers" : ["chest_foot_locked"]
}
}
Contents = {
"occupants" : {
"player_id" : [ "player_id" ],
"NPC" : ["barkeep", "cook", "barmaid", "wine steward"],
"monster" : ["chicken_1", "rat_1", "rat_2"]
},
"structure" : ["wall", "wall", "wall", "wall", "door_1", "window_1"],
"props" : {
"media" : ["book"],
"consumable" : ["meat on bone"],
"kitchen" : ["bowel_wood", "cup_tin", "bottle_glass_empty"],
"lights" : ["tri_candle_stand"],
"furniture" : ["shoe_wrack", "table", "wardrobe_wood", "chair_wood", "bed_queen", "table_side_wood"],
"drapery" : ["rug_large", "bed_canopy", "shirt_brown"],
"containers" : ["chest_foot_locked"]
}
}
No comments:
Post a Comment
Conduct: Be nice and don't advertise or plug without adding value to the conversation.