8ccecd68 by Barry

Added soul plates, reflectors and messaging for pankration.

1 parent 71937a50
...@@ -247,26 +247,101 @@ def db_get_pankration_record(member_id): ...@@ -247,26 +247,101 @@ def db_get_pankration_record(member_id):
247 pan_record.close() 247 pan_record.close()
248 return dict_factory(c, result) 248 return dict_factory(c, result)
249 249
250 def db_add_monster(member_id, monster): 250 def db_add_soul_plate(member_id, soul_plate):
251 pan_record = db_get_pankration_record(member_id) 251 pan_record = db_get_pankration_record(member_id)
252 log("{}".format(member_id)) 252 log("{}".format(member_id))
253 conn = sqlite3.connect('db.sqlite3') 253 conn = sqlite3.connect('db.sqlite3')
254 c = conn.cursor() 254 c = conn.cursor()
255 db_state = c.execute("SELECT monster_inventory FROM pankration WHERE member_id = ?;", (member_id,)).fetchone() 255 db_state = c.execute("SELECT soul_plates, member_id FROM pankration WHERE member_id = ?;", (member_id,)).fetchone()
256 if not db_state: 256 if not db_state:
257 c.execute("""INSERT INTO pankration(member_id, wins, losses, monster_inventory) 257 log("no record")
258 VALUES(?, ?, ?, ?);""", (member_id, 0, 0, pickle.dumps([monster]))) 258 c.execute("""INSERT INTO pankration(member_id, wins, losses, soul_plates)
259 VALUES(?, ?, ?, ?);""", (member_id, 0, 0, pickle.dumps([soul_plate])))
259 conn.commit() 260 conn.commit()
260 else: 261 else:
261 log(db_state) 262 log(db_state)
262 inv = str(db_state[0]) 263 if db_state[0] and len(db_state[0]) > 0:
263 log(inv) 264 inv = str(db_state[0])
264 monster_inventory = pickle.loads(inv) 265 soul_plates = pickle.loads(inv)
265 monster_inventory.append(monster) 266 else:
266 c.execute("""UPDATE pankration SET monster_inventory = ? 267 soul_plates = []
267 WHERE member_id = ?;""", (pickle.dumps(monster_inventory), member_id)) 268 soul_plates.append(soul_plate)
269 c.execute("""UPDATE pankration SET soul_plates = ?
270 WHERE member_id = ?;""", (pickle.dumps(soul_plates), member_id))
271 conn.commit()
272
273 def db_remove_soul_plate(member_id, idx):
274 pan_record = db_get_pankration_record(member_id)
275 log("{}".format(member_id))
276 conn = sqlite3.connect('db.sqlite3')
277 c = conn.cursor()
278 db_state = c.execute("SELECT soul_plates, member_id FROM pankration WHERE member_id = ?;", (member_id,)).fetchone()
279 if not db_state:
280 log("Invalid remove request for reflector: {}".format(idx,))
281 return False
282 else:
283 log(db_state)
284 if db_state[0] and len(db_state[0]) > 0:
285 inv = str(db_state[0])
286 soul_plates = pickle.loads(inv)
287 else:
288 log("Invalid remove request for reflector: {}".format(idx,))
289 return False
290 del soul_plates[idx]
291 c.execute("""UPDATE pankration SET soul_plates = ?
292 WHERE member_id = ?;""", (pickle.dumps(soul_plates), member_id))
293 conn.commit()
294
295 def db_add_reflector(member_id, reflector):
296 pan_record = db_get_pankration_record(member_id)
297 log("{}".format(member_id))
298 conn = sqlite3.connect('db.sqlite3')
299 c = conn.cursor()
300 db_state = c.execute("SELECT reflectors, member_id FROM pankration WHERE member_id = ?;", (member_id,)).fetchone()
301 if not db_state:
302 log("no record")
303 c.execute("""INSERT INTO pankration(member_id, wins, losses, reflectors)
304 VALUES(?, ?, ?, ?);""", (member_id, 0, 0, pickle.dumps([reflector])))
305 conn.commit()
306 else:
307 log(db_state)
308 if db_state[0] and len(db_state[0]) > 0:
309 inv = str(db_state[0])
310 reflectors = pickle.loads(inv)
311 else:
312 reflectors = []
313 reflectors.append(reflector)
314 c.execute("""UPDATE pankration SET reflectors = ?
315 WHERE member_id = ?;""", (pickle.dumps(reflectors), member_id))
268 conn.commit() 316 conn.commit()
269 317
318 def db_remove_reflector(member_id, idx):
319 pan_record = db_get_pankration_record(member_id)
320 log("{}".format(member_id))
321 conn = sqlite3.connect('db.sqlite3')
322 c = conn.cursor()
323 db_state = c.execute("SELECT reflectors, member_id FROM pankration WHERE member_id = ?;", (member_id,)).fetchone()
324 if not db_state:
325 log("Invalid remove request for reflector: {}".format(idx,))
326 return False
327 else:
328 log(db_state)
329 if db_state[0] and len(db_state[0]) > 0:
330 inv = str(db_state[0])
331 reflectors = pickle.loads(inv)
332 else:
333 log("Invalid remove request for reflector: {}".format(idx,))
334 return False
335 del reflectors[idx]
336 c.execute("""UPDATE pankration SET reflectors = ?
337 WHERE member_id = ?;""", (pickle.dumps(reflectors), member_id))
338 conn.commit()
339
340 def db_convert_soul_plate_to_reflector(member_id, soul_plate, idx):
341 db_add_reflector(member_id, soul_plate)
342 db_remove_soul_plate(member_id, idx)
343
344
270 def db_get_member(discord_id=None, username=None): 345 def db_get_member(discord_id=None, username=None):
271 # Do a lookup by ID, if it's found but the name doesn't match then add a row to aliases with the previous name and change the member name 346 # Do a lookup by ID, if it's found but the name doesn't match then add a row to aliases with the previous name and change the member name
272 member_conn = sqlite3.connect('db.sqlite3') 347 member_conn = sqlite3.connect('db.sqlite3')
......
No preview for this file type
...@@ -85,7 +85,11 @@ registered_commands = {'!help': 'do_help', '!commands': 'do_help', ...@@ -85,7 +85,11 @@ registered_commands = {'!help': 'do_help', '!commands': 'do_help',
85 '!rigged': 'do_rigged', 85 '!rigged': 'do_rigged',
86 '!listzones': 'do_list_zones', 86 '!listzones': 'do_list_zones',
87 '!huntmonster': 'do_hunt_monster', 87 '!huntmonster': 'do_hunt_monster',
88 '!listmonster': 'do_list_monsters', 88 '!listferalskills': 'do_list_feral_skills', '!listferalskill': 'do_list_feral_skills',
89 '!listreflectors': 'do_list_reflectors', '!listreflector': 'do_list_reflectors',
90 '!listsoulplates': 'do_list_soul_plates', '!listsoulplate': 'do_list_soul_plates',
91 '!convertplate': 'do_convert_plate', '!convertsoulplate': 'do_convert_plate',
92 '!pankration': 'do_pankration',
89 } 93 }
90 94
91 95
...@@ -1015,34 +1019,116 @@ def do_rigged(client, message_parts, message): ...@@ -1015,34 +1019,116 @@ def do_rigged(client, message_parts, message):
1015 send_message(client, message.channel, ":musical_note: {} :musical_note:".format(random.choice(lines))) 1019 send_message(client, message.channel, ":musical_note: {} :musical_note:".format(random.choice(lines)))
1016 return 1020 return
1017 1021
1018 def do_list_monsters(client, message_parts, message): 1022 #### PANKRATION
1023
1024
1025 def do_pankration(client, message_parts, message):
1026 send_message(client, message.channel, """**NOTE! This is NOT implemented yet.. only partially**
1027 {} Available Commands:
1028
1029 *Hunting for Soul Plates:*
1030 **!listzones** - Returns a list of zones available for hunting and how many credits it costs to search in that zone. Depending on the weather and other factors some zones may not always be available.
1031 **!huntmonster <zone>** - An attempt will be made to search for a soul plate (monster) in the zone specified. Each search costs a certain amount of credits. Each zone has a different cost.
1032
1033 *Viewing Your Inventory:*
1034 **!listsoulplates** - Returns a list of all soul plates you have in your posession.
1035 **!listreflectors** - Returns a list of all reflectors you have in your posession (The available monsters you can fight with).
1036 **!listferalskills** - Returns a list of all feral skills you have in your inventory
1037
1038 *Editing Your Collections:*
1039 **!convertplate <plate number> <convert_to>** - From the list of soul plates you can choose to either convert the plate into a \"reflector\" or \"skill\".
1040 Ex: **!convertplate 1 reflector**
1041 **!convertplate 4 skill**
1042 **!assignskill <reflector number> <skill num>** - Assigns a skill to a reflector. Each skill is worth a certain amount of feral points, each monster has a maximum of feral points available.
1043
1044 *Arena Battle:*
1045 **!registerbattle <reflector number>** - Adds your reflector to the queue in the arena. When the arena is available your monster will be paired with either another players monster or a similarly matched arena monster.
1046 **!registerbattle <reflector number> <player name>** - If you want to challenge a specific user to a battle just provide their user name. Have them do the same and your battle will start when the arena is available.
1047
1048 """.format(message.author.mention()))
1049
1050 def do_convert_plate(client, message_parts, message):
1051 member = data.db_get_member(message.author.id)
1052
1053 pankration_data = data.db_get_pankration_record(member['member_id'])
1054 if pankration_data and pankration_data['soul_plates']:
1055 log(message_parts)
1056 if len(message_parts) < 2:
1057 send_message(client, message.channel, 'You must provide at least 2 arguments for converting a plate. The plate number and the type of conversion. Please see !pankration for an example.')
1058 return
1059
1060 plate_num = message_parts[0]
1061 convert_to = message_parts[1]
1062
1063 soul_plates = pickle.loads(str(pankration_data['soul_plates']))
1064 if not plate_num.isdigit() or int(plate_num) < 1 or int(plate_num) > len(soul_plates):
1065 send_message(client, message.channel, 'The requested plate is invalid. Please provide the number from !listsoulplates')
1066 return
1067 plate_num = int(plate_num)
1068 if convert_to == "reflector":
1069 # do reflector stuff
1070 data.db_convert_soul_plate_to_reflector(member['member_id'], soul_plates[plate_num], plate_num)
1071 pass
1072 elif convert_to == "skill":
1073 # do skill stuff
1074 pass
1075 else:
1076 send_message(client, message.channel, 'A plate can only be converted into a reflector or skill. Please see !pankration for an example.')
1077 return
1078
1079 #send_message(client, message.channel, "\n\n".join("{}. {}".format(idx+1, str(soul_plate)) for idx, soul_plate in enumerate(soul_plates)))
1080 else:
1081 send_message(client, message.channel, 'You have no soul plates to convert.')
1082
1083 def do_list_soul_plates(client, message_parts, message):
1019 member = data.db_get_member(message.author.id) 1084 member = data.db_get_member(message.author.id)
1020 log(member) 1085
1021 monster_data = data.db_get_pankration_record(member['member_id']) 1086 pankration_data = data.db_get_pankration_record(member['member_id'])
1022 if monster_data: 1087 if pankration_data and pankration_data['soul_plates']:
1023 monsters = pickle.loads(str(monster_data['monster_inventory'])) 1088 soul_plates = pickle.loads(str(pankration_data['soul_plates']))
1024 send_message(client, message.channel, "\n\n".join(str(monster) for monster in monsters)) 1089 send_message(client, message.channel, "\n\n".join("{}. {}".format(idx+1, str(soul_plate.get_soul_plate_description())) for idx, soul_plate in enumerate(soul_plates)))
1025 else: 1090 else:
1026 send_message(client, message.channel, 'You have no monsters.') 1091 send_message(client, message.channel, 'You have no soul plates.')
1092
1093 def do_list_reflectors(client, message_parts, message):
1094 member = data.db_get_member(message.author.id)
1095
1096 pankration_data = data.db_get_pankration_record(member['member_id'])
1097 if pankration_data and pankration_data['reflectors']:
1098 reflectors = pickle.loads(str(pankration_data['reflectors']))
1099 send_message(client, message.channel, "\n\n".join("{}. {}".format(idx+1, str(reflector)) for idx, reflector in enumerate(reflectors)))
1100 else:
1101 send_message(client, message.channel, 'You have no reflectors.')
1102
1103
1104 def do_list_feral_skills(client, message_parts, message):
1105 member = data.db_get_member(message.author.id)
1106
1107 pankration_data = data.db_get_pankration_record(member['member_id'])
1108 if pankration_data and pankration_data['feral_skills']:
1109 feral_skills = pickle.loads(str(pankration_data['feral_skills']))
1110 send_message(client, message.channel, "\n\n".join("{}. {}".format(idx+1, str(feral_skill)) for idx, feral_skill in enumerate(feral_skills)))
1111 else:
1112 send_message(client, message.channel, 'You have no feral skills.')
1027 1113
1028 def do_hunt_monster(client, message_parts, message): 1114 def do_hunt_monster(client, message_parts, message):
1029 p = Pankration() 1115 p = Pankration()
1030 hunt_response = p.hunt_monster(' '.join(message_parts)) 1116 hunt_response = p.hunt_monster(' '.join(message_parts))
1031 str_out = hunt_response.message + "\n\n" 1117 str_out = hunt_response.message + "\n\n"
1032 if hunt_response.result == HuntResponse.SUCCESS: 1118 if hunt_response.result == HuntResponse.SUCCESS:
1033 monster = hunt_response.monster 1119 soul_plate = hunt_response.monster
1034 member = data.db_get_member(message.author.id) 1120 member = data.db_get_member(message.author.id)
1035 data.db_add_monster(member['member_id'], monster) 1121 data.db_add_soul_plate(member['member_id'], soul_plate)
1036 str_out += str(monster) 1122 str_out += str(soul_plate.get_soul_plate_description())
1037 send_message(client, message.channel, str_out) 1123 send_message(client, message.channel, str_out)
1038
1039 return
1040 1124
1041 def do_list_zones(client, message_parts, message): 1125 def do_list_zones(client, message_parts, message):
1042 p = Pankration() 1126 p = Pankration()
1043 send_message(client, message.channel, ', '.join(p.list_zones())) 1127 send_message(client, message.channel, ', '.join(p.list_zones()))
1044 return 1128 return
1045 1129
1130
1131 ### END PANKRATION
1046 def start_timer(client): 1132 def start_timer(client):
1047 needs_loot = True 1133 needs_loot = True
1048 while not quitting: 1134 while not quitting:
......
...@@ -79,6 +79,31 @@ class Jobs: ...@@ -79,6 +79,31 @@ class Jobs:
79 members = [attr for attr in dir(Jobs()) if not callable(attr) and not attr.startswith("__") and not attr.startswith("get_job_name")] 79 members = [attr for attr in dir(Jobs()) if not callable(attr) and not attr.startswith("__") and not attr.startswith("get_job_name")]
80 return members[job-1] 80 return members[job-1]
81 81
82 evasion_by_job = {
83 Jobs.BLM: {'base_eva': 4, 'eva_per_level': 2.48},
84 Jobs.BLU: {'base_eva': 5, 'eva_per_level': 2.78},
85 Jobs.BRD: {'base_eva': 4, 'eva_per_level': 2.66},
86 Jobs.BST: {'base_eva': 5, 'eva_per_level': 2.78},
87 Jobs.COR: {'base_eva': 4, 'eva_per_level': 2.66},
88 Jobs.DNC: {'base_eva': 5, 'eva_per_level': 2.88},
89 Jobs.DRG: {'base_eva': 5, 'eva_per_level': 2.88},
90 Jobs.DRK: {'base_eva': 5, 'eva_per_level': 2.78},
91 Jobs.GEO: {'base_eva': 4, 'eva_per_level': 2.66},
92 Jobs.MNK: {'base_eva': 5, 'eva_per_level': 2.88},
93 Jobs.NIN: {'base_eva': 6, 'eva_per_level': 3},
94 Jobs.PLD: {'base_eva': 5, 'eva_per_level': 2.78},
95 Jobs.PUP: {'base_eva': 5, 'eva_per_level': 2.88},
96 Jobs.RDM: {'base_eva': 4, 'eva_per_level': 2.66},
97 Jobs.RNG: {'base_eva': 4, 'eva_per_level': 2.48},
98 Jobs.RUN: {'base_eva': 5, 'eva_per_level': 2.88},
99 Jobs.SAM: {'base_eva': 5, 'eva_per_level': 2.88},
100 Jobs.SCH: {'base_eva': 4, 'eva_per_level': 2.48},
101 Jobs.SMN: {'base_eva': 4, 'eva_per_level': 2.48},
102 Jobs.THF: {'base_eva': 6, 'eva_per_level': 3},
103 Jobs.WAR: {'base_eva': 5, 'eva_per_level': 2.78},
104 Jobs.WHM: {'base_eva': 4, 'eva_per_level': 2.48},
105 }
106
82 TemperamentPosture = { 107 TemperamentPosture = {
83 4: {"name": "Very Agressive", "message": "Show no mercy!", "value": 4}, 108 4: {"name": "Very Agressive", "message": "Show no mercy!", "value": 4},
84 3: {"name": "Somewhat Agressive", "message": "Give em' a little more bite!", "value": 3}, 109 3: {"name": "Somewhat Agressive", "message": "Give em' a little more bite!", "value": 3},
...@@ -297,9 +322,28 @@ class Monster: ...@@ -297,9 +322,28 @@ class Monster:
297 self.base_dex = family['base_dex'] 322 self.base_dex = family['base_dex']
298 self.dex_per_level = family['dex_per_level'] 323 self.dex_per_level = family['dex_per_level']
299 self.hp = self.get_hp() 324 self.hp = self.get_hp()
325 self.wins = 0
326 self.losses = 0
300 327
301 def __str__(self): 328 def __str__(self):
302 return "**Stats:**\nFamily: {}\nLevel: {}\nMain Job: {}\nSupport Job: {}\nInnate Feral Skills: {}\nEquipped Feral Skills: {}\nFeral Points: {}".format(self.family_name, self.level, Jobs().get_job_name(self.main_job), Jobs().get_job_name(self.support_job), ', '.join(self.innate_feral_skills), ', '.join(self.equipped_feral_skills), self.get_fp()) 329 try:
330 return "**{}**\n*Stats:*\nFamily: {}\nLevel: {}\nMain Job: {}\nSupport Job: {}\nInnate Feral Skills: {}\nEquipped Feral Skills: {}\nFeral Points: {}\n\nWins: {}\nLosses: {}".format(self.monster_type, self.family_name, self.level, Jobs().get_job_name(self.main_job), Jobs().get_job_name(self.support_job), ', '.join(self.innate_feral_skills), ', '.join(self.equipped_feral_skills), self.get_fp(), self.wins, self.losses)
331 except AttributeError:
332 return "Old Format monster, unable to display."
333 #return "Family: {}\nLevel: {}\nMain Job: {}\nSupport Job: {}\nInnate Feral Skills: {}\nEquipped Feral Skills: {}\nDicipline Level: {}\nTemperament...".format(self.family, self.level, self.main_job, self.support_job, self.innate_feral_skills, self.equipped_feral_skills, self.discipline_level)
334
335 def get_soul_plate_description(self):
336 try:
337 return "*Family:*\n**{}**\nJob Trait: {}\nFeral Points: {}".format(self.family_name, Jobs().get_job_name(self.main_job), self.get_fp())
338 except AttributeError:
339 return "Old Format monster, unable to display."
340 #return "Family: {}\nLevel: {}\nMain Job: {}\nSupport Job: {}\nInnate Feral Skills: {}\nEquipped Feral Skills: {}\nDicipline Level: {}\nTemperament...".format(self.family, self.level, self.main_job, self.support_job, self.innate_feral_skills, self.equipped_feral_skills, self.discipline_level)
341
342 def get_reflector_description(self):
343 try:
344 return "**{}**\n*Stats:*\nFamily: {}\nLevel: {}\nMain Job: {}\nSupport Job: {}\nInnate Feral Skills: {}\nEquipped Feral Skills: {}\nFeral Points: {}\n\nWins: {}\nLosses: {}".format(self.monster_type, self.family_name, self.level, Jobs().get_job_name(self.main_job), Jobs().get_job_name(self.support_job), ', '.join(self.innate_feral_skills), ', '.join(self.equipped_feral_skills), self.get_fp(), self.wins, self.losses)
345 except AttributeError:
346 return "Old Format monster, unable to display."
303 #return "Family: {}\nLevel: {}\nMain Job: {}\nSupport Job: {}\nInnate Feral Skills: {}\nEquipped Feral Skills: {}\nDicipline Level: {}\nTemperament...".format(self.family, self.level, self.main_job, self.support_job, self.innate_feral_skills, self.equipped_feral_skills, self.discipline_level) 347 #return "Family: {}\nLevel: {}\nMain Job: {}\nSupport Job: {}\nInnate Feral Skills: {}\nEquipped Feral Skills: {}\nDicipline Level: {}\nTemperament...".format(self.family, self.level, self.main_job, self.support_job, self.innate_feral_skills, self.equipped_feral_skills, self.discipline_level)
304 348
305 def get_hp(self): 349 def get_hp(self):
...@@ -336,11 +380,25 @@ class Monster: ...@@ -336,11 +380,25 @@ class Monster:
336 else: 380 else:
337 return "Obedient" 381 return "Obedient"
338 382
383 def get_combat_skill(self):
384 # This is a very very complicated relationship betwen job and weapon type and how often it is used.
385 # We are going to generalize it since it's a pain in the ass and just take the average A+ rating and get the cap for the current level
386 return int(round(max(5, self.level * 2.88)))
387
388
339 def get_dexterity(self): 389 def get_dexterity(self):
340 return int(round(max(self.base_dex, self.level * self.dex_per_level))) 390 return int(round(max(self.base_dex, self.level * self.dex_per_level)))
341 391
342 def get_accuracy(self): 392 def get_accuracy(self):
343 return int(math.floor(3*self.get_dexterity()/4) + 100) 393 # We ignore magic / ranged / melee here and give everyone a good acc. This could be improved by doing a lookup for each type and based on the
394 # type of monster (magic, range, or melee) then adjust the combat skill according to what type of attack is being performed.
395 return int(math.floor(3*self.get_dexterity()/4) + self.get_combat_skill())
396
397 def get_evasion(self):
398 job_eva = evasion_by_job[self.main_job]
399 base_eva = int(round(max(job_eva['base_eva'], self.level * job_eva['eva_per_level'])))
400
401 return base_eva + int(self.get_agility() / 2)
344 402
345 def get_vitality(self): 403 def get_vitality(self):
346 return int(round(max(self.base_vit, self.level * self.vit_per_level))) 404 return int(round(max(self.base_vit, self.level * self.vit_per_level)))
...@@ -358,6 +416,14 @@ class Monster: ...@@ -358,6 +416,14 @@ class Monster:
358 print(self.hp) 416 print(self.hp)
359 return max(0, int(round((self.hp/self.get_hp())*100))) 417 return max(0, int(round((self.hp/self.get_hp())*100)))
360 418
419 def get_hit_rate(self, enemy_eva, level_difference):
420 rate = 75 + math.floor(((self.get_accuracy() - enemy_eva)/2)) - (2*level_difference)
421 if rate < 20:
422 rate = 20
423 elif rate > 95:
424 rate = 95
425 return rate
426
361 # Calculate the base damage against the provided defense 427 # Calculate the base damage against the provided defense
362 # attack_type can be 'ranged' or 'melee' 428 # attack_type can be 'ranged' or 'melee'
363 def get_physical_base_damage(self, defense, attack_type, level_difference, enemy_vit): 429 def get_physical_base_damage(self, defense, attack_type, level_difference, enemy_vit):
...@@ -421,6 +487,9 @@ class Monster: ...@@ -421,6 +487,9 @@ class Monster:
421 phy_damage = self.get_physical_base_damage(monster.get_base_defense(), 'melee', monster.level - self.level, monster.get_vitality()) 487 phy_damage = self.get_physical_base_damage(monster.get_base_defense(), 'melee', monster.level - self.level, monster.get_vitality())
422 return (phy_damage, 'hits') 488 return (phy_damage, 'hits')
423 489
490 def is_a_hit(self, monster):
491 hit_rate = self.get_hit_rate(monster.get_evasion(), monster.level - self.level)
492 return random.randint(1, 100) < hit_rate
424 493
425 def apply_damage(self, damage): 494 def apply_damage(self, damage):
426 self.hp -= damage 495 self.hp -= damage
...@@ -458,6 +527,12 @@ class AttackAction(Action): ...@@ -458,6 +527,12 @@ class AttackAction(Action):
458 self.damage = damage 527 self.damage = damage
459 self.message = message 528 self.message = message
460 529
530 class MissAction(Action):
531 def __init__(self, attacker, target, message):
532 self.attacker = attacker
533 self.target = target
534 self.message = message
535
461 class DefeatAction(Action): 536 class DefeatAction(Action):
462 def __init__(self, attacker, target, message, xp): 537 def __init__(self, attacker, target, message, xp):
463 self.attacker = attacker 538 self.attacker = attacker
...@@ -465,6 +540,7 @@ class DefeatAction(Action): ...@@ -465,6 +540,7 @@ class DefeatAction(Action):
465 self.message = message 540 self.message = message
466 self.xp = xp 541 self.xp = xp
467 542
543
468 class Arena: 544 class Arena:
469 545
470 def __init__(self, monster1, monster2, battle_type): 546 def __init__(self, monster1, monster2, battle_type):
...@@ -489,26 +565,33 @@ class Arena: ...@@ -489,26 +565,33 @@ class Arena:
489 primary = self.monster2 565 primary = self.monster2
490 secondary = self.monster1 566 secondary = self.monster1
491 567
492 result1 = primary.attack(secondary) 568 if primary.is_a_hit(secondary):
493 secondary.apply_damage(result1[0]) 569 result1 = primary.attack(secondary)
494 actions.append(AttackAction(primary, secondary, result1[0], result1[1])) 570 secondary.apply_damage(result1[0])
495 if secondary.hp <= 0: 571 actions.append(AttackAction(primary, secondary, result1[0], result1[1]))
496 level_difference = secondary.level - primary.level 572 if secondary.hp <= 0:
497 if level_difference in exp_table: 573 level_difference = secondary.level - primary.level
498 xp = exp_table[level_difference] 574 if level_difference in exp_table:
499 elif level_difference > 15: 575 xp = exp_table[level_difference]
500 xp = exp_table[15] 576 elif level_difference > 15:
501 else: 577 xp = exp_table[15]
502 xp = 0 578 else:
503 actions.append(DefeatAction(primary, secondary, 'was defeated', xp)) 579 xp = 0
504 return actions 580 actions.append(DefeatAction(primary, secondary, 'was defeated', xp))
505 result2 = secondary.attack(primary) 581 return actions
506 primary.apply_damage(result2[0]) 582 else:
507 actions.append(AttackAction(secondary, primary, result2[0], result2[1])) 583 actions.append(MissAction(primary, secondary, 'missed'))
508 if primary.hp <= 0: 584
509 xp = 200 + (20 * (primary.level - secondary.level)) 585 if secondary.is_a_hit(primary):
510 actions.append(DefeatAction(secondary, primary, 'was defeated', xp)) 586 result2 = secondary.attack(primary)
511 return actions 587 primary.apply_damage(result2[0])
588 actions.append(AttackAction(secondary, primary, result2[0], result2[1]))
589 if primary.hp <= 0:
590 xp = 200 + (20 * (primary.level - secondary.level))
591 actions.append(DefeatAction(secondary, primary, 'was defeated', xp))
592 return actions
593 else:
594 actions.append(MissAction(secondary, primary, 'missed'))
512 return actions 595 return actions
513 596
514 597
...@@ -552,7 +635,10 @@ if __name__ == "__main__": ...@@ -552,7 +635,10 @@ if __name__ == "__main__":
552 635
553 636
554 print("Acc: {}".format(monster.get_accuracy())) 637 print("Acc: {}".format(monster.get_accuracy()))
638 print("Eva: {}".format(monster.get_evasion()))
639
555 print("Acc: {}".format(monster2.get_accuracy())) 640 print("Acc: {}".format(monster2.get_accuracy()))
641 print("Eva: {}".format(monster2.get_evasion()))
556 642
557 battle_arena = p.start_battle(monster, monster2, "derp") 643 battle_arena = p.start_battle(monster, monster2, "derp")
558 fighting = True 644 fighting = True
...@@ -560,6 +646,8 @@ if __name__ == "__main__": ...@@ -560,6 +646,8 @@ if __name__ == "__main__":
560 actions = battle_arena.step() 646 actions = battle_arena.step()
561 time.sleep(2) 647 time.sleep(2)
562 for action in actions: 648 for action in actions:
649 if isinstance(action, MissAction):
650 print("{} {} {}.".format(action.attacker.monster_type, action.message, action.target.monster_type))
563 if isinstance(action, AttackAction): 651 if isinstance(action, AttackAction):
564 print("{} {} {} for {}.".format(action.attacker.monster_type, action.message, action.target.monster_type, action.damage)) 652 print("{} {} {} for {}.".format(action.attacker.monster_type, action.message, action.target.monster_type, action.damage))
565 if isinstance(action, DefeatAction): 653 if isinstance(action, DefeatAction):
......