-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathworld.py
More file actions
222 lines (180 loc) · 6.25 KB
/
world.py
File metadata and controls
222 lines (180 loc) · 6.25 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
import random
import enemies
import npc
class MapTile:
def __init__(self, x, y):
self.x = x
self.y = y
def intro_text(self):
raise NotImplementedError("Create a subclass instead!")
def modify_player(self, player):
pass
class StartTile(MapTile):
def intro_text(self):
return """
You find yourself in a cave with a flickering torch on the wall.
You can make out four paths, each equally as dark and foreboding.
"""
class BoringTile(MapTile):
def intro_text(self):
return """
This is a very boring part of the cave.
"""
class VictoryTile(MapTile):
def modify_player(self, player):
player.victory = True
def intro_text(self):
return """
You see a bright light in the distance...
... it grows as you get closer! It's sunlight!
Victory is yours!
"""
class EnemyTile(MapTile):
def __init__(self, x, y):
r = random.random()
if r < 0.50:
self.enemy = enemies.GiantSpider()
self.alive_text = "A giant spider jumps down from " \
"its web in front of you!"
self.dead_text = "The corpse of a dead spider " \
"rots on the ground."
elif r < 0.80:
self.enemy = enemies.Ogre()
self.alive_text = "An ogre is blocking your path!"
self.dead_text = "A dead ogre reminds you of your triumph."
elif r < 0.95:
self.enemy = enemies.BatColony()
self.alive_text = "You hear a squeaking noise growing louder" \
"...suddenly you are lost in s swarm of bats!"
self.dead_text = "Dozens of dead bats are scattered on the ground."
else:
self.enemy = enemies.RockMonster()
self.alive_text = "You've disturbed a rock monster " \
"from his slumber!"
self.dead_text = "Defeated, the monster has reverted " \
"into an ordinary rock."
super().__init__(x, y)
def intro_text(self):
return self.alive_text if self.enemy.is_alive() else self.dead_text
def modify_player(self, player):
if self.enemy.is_alive():
player.hp -= self.enemy.damage
print("Enemy does {} damage. You have {} HP remaining.".format(
self.enemy.damage, player.hp))
class TraderTile(MapTile):
def __init__(self, x, y):
self.trader = npc.Trader()
super().__init__(x, y)
def trade(self, buyer, seller):
for i, item in enumerate(seller.invintory, 1):
print("{}. {} - {} Gold".format(i, item.name, item.value))
while True:
user_input = input("Choose an item or press Q to exit: ")
if user_input in ['Q', 'q']:
return
else:
try:
choice = int(user_input)
to_swap = seller.inventory[choice - 1]
self.swap(seller, buyer, to_swap)
except ValueError:
print("Invalid choice!")
def swap(self, seller, buyer, item):
if item.value > buyer.gold:
print("That's too expensive")
return
seller.inventory.remove(item)
buyer.inventory.append(item)
seller.gold = seller.gold + item.value
buyer.gold = buyer.gold - item.value
print("Trade complete!")
def check_if_trade(self, player):
while True:
print("Would you like to (B)uy, (S)ell, or (Q)uit?")
user_input = input()
if user_input in ['Q', 'q']:
return
elif user_input in ['B', 'b']:
print("Here's whats available to buy: ")
self.trade(buyer=player, seller=self.trader)
elif user_input in ['S', 's']:
print("Here's whats available to sell: ")
self.trade(buyer=self.trader, seller=player)
else:
print("Invalid choice!")
def intro_text(self):
return """
A frail not-quite-human, not-quite-creature squats in the corner
clinking his gold coins together. He looks willing to trade.
"""
class FindGoldTile(MapTile):
def __init__(self, x, y):
self.gold = random.randint(1, 50)
self.gold_claimed = False
super().__init__(x, y)
def modify_player(self, player):
if not self.gold_claimed:
self.gold_claimed = True
player.gold = player.gold + self.gold
print("+{} gold added.".format(self.gold))
def intro_text(self):
if self.gold_claimed:
return """
Another unremarkable part of the cave. You must forge onwards.
"""
else:
return """
Someone dropped some gold. You pick it up.
"""
world_map = []
start_tile_location = None
tile_type_dict = {
"VT": VictoryTile,
"EN": EnemyTile,
"ST": StartTile,
"FG": FindGoldTile,
"TT": TraderTile,
" ": None
}
def tile_at(x, y):
if x < 0 or y < 0:
return None
try:
return world_map[y][x]
except IndexError:
return None
def is_dsl_valid(dsl):
if dsl.count("|ST|") != 1:
return False
if dsl.count("|VT|") == 0:
return False
lines = dsl.splitlines()
lines = [l for l in lines if l]
pipe_counts = [line.count("|") for line in lines]
for count in pipe_counts:
if count != pipe_counts[0]:
return False
return True
def parse_world_dsl():
if not is_dsl_valid(world_dsl):
raise SyntaxError("DSL is invalid!")
dsl_lines = world_dsl.splitlines()
dsl_lines = [x for x in dsl_lines if x]
for y, dsl_row in enumerate(dsl_lines):
row = []
dsl_cells = dsl_row.split("|")
dsl_cells = [c for c in dsl_cells if c]
for x, dsl_cell in enumerate(dsl_cells):
tile_type = tile_type_dict[dsl_cell]
if tile_type == StartTile:
global start_tile_location
start_tile_location = x, y
row.append(tile_type(x, y) if tile_type else None)
world_map.append(row)
world_dsl = """
|EN|EN|VT|EN|EN|
|EN| | | |EN|
|EN|FG|EN| |TT|
|TT| |ST|FG|EN|
|FG| |EN| |FG|
"""