Updated to use external tsv files for ids.
This commit is contained in:
parent
6e0ceaf239
commit
13073df432
|
@ -95,3 +95,5 @@
|
|||
2729 Monster bite
|
||||
2798 Received an electric shock
|
||||
2843 I was held as a slave
|
||||
3311 Sleeping comfortably
|
||||
3327 No entertainment
|
|
178
sheditor.py
178
sheditor.py
|
@ -2,6 +2,7 @@ import argparse
|
|||
import copy
|
||||
import os
|
||||
import datetime
|
||||
import csv
|
||||
from bs4 import BeautifulSoup
|
||||
|
||||
import rich
|
||||
|
@ -16,83 +17,32 @@ storage_ids = {
|
|||
3062: {"name": "Body storage", "capacity": 20},
|
||||
}
|
||||
|
||||
char_skills = {
|
||||
1: "Piloting", # Likely deprecated - now using code 22
|
||||
2: "Mining",
|
||||
3: "Botany",
|
||||
4: "Construction",
|
||||
5: "Industry",
|
||||
6: "Medical",
|
||||
7: "Gunner",
|
||||
8: "Shielding",
|
||||
9: "Operations",
|
||||
10: "Weapons",
|
||||
11: "Unknown-11",
|
||||
12: "Logistics", # All characters seem to have this but it doesn't show up in the UI
|
||||
13: "Unknown-13", # All characters seem to have this skill but what is it for?
|
||||
14: "Navigation",
|
||||
15: "Unknown-15",
|
||||
16: "Research",
|
||||
22: "Piloting", # Appears to be the new piloting code?
|
||||
}
|
||||
|
||||
char_attributes = {
|
||||
210: "Bravery",
|
||||
214: "Preception",
|
||||
213: "Intelligence",
|
||||
212: "Zest",
|
||||
}
|
||||
|
||||
char_traits = {
|
||||
"Iron Stomach": 1533,
|
||||
"Spacefarer": 1045,
|
||||
"Confident": 1046,
|
||||
"Hard Working": 1041,
|
||||
"Antisocial": 1037,
|
||||
"Nyctophilia": 1534,
|
||||
"Wimp": 655,
|
||||
"Clumsy": 656,
|
||||
"Charming": 1048,
|
||||
"Bloodlust": 1036,
|
||||
"Fast Learner": 1039,
|
||||
"Minimalist": 1535,
|
||||
"Lazy": 1040,
|
||||
"Neurotic": 1047,
|
||||
"Alien Lover": 2082,
|
||||
"Needy": 1038,
|
||||
"Peace-loving": 1043,
|
||||
"Suicidal": 1034,
|
||||
"Smart": 1035,
|
||||
"Psychopath": 1042,
|
||||
"Hero": 191,
|
||||
"Talkative": 1560,
|
||||
"Iron-Willed": 1044,
|
||||
"Gourmand": 1562,
|
||||
}
|
||||
|
||||
|
||||
class ItemCodeDatabase:
|
||||
|
||||
def __init__(self, database_filename):
|
||||
self.id_dict = {}
|
||||
|
||||
for line in open(database_filename):
|
||||
result = line.split()
|
||||
code = int(result[0])
|
||||
name = ' '.join(result[1:])
|
||||
# print(code, name)
|
||||
self.id_dict[code] = name
|
||||
|
||||
def get_name_from_code(self, code):
|
||||
return self.id_dict[code]
|
||||
|
||||
def validate_code(self, code):
|
||||
return code in self.id_dict
|
||||
|
||||
|
||||
# A single item with its code, name, and quantity
|
||||
class Item:
|
||||
|
||||
item_ids = None
|
||||
|
||||
@classmethod
|
||||
def load_ids(cls, item_filename):
|
||||
if cls.item_ids is not None:
|
||||
return
|
||||
else:
|
||||
cls.item_ids = {}
|
||||
|
||||
with open(item_filename, 'r') as item_file:
|
||||
item_reader = csv.reader(item_file, delimiter='\t')
|
||||
for row in item_reader:
|
||||
cls.item_ids[int(row[0])] = row[1].strip()
|
||||
|
||||
@classmethod
|
||||
def get_name_from_code(cls, code):
|
||||
return cls.item_ids.get(code, None) if cls.item_ids is not None else None
|
||||
|
||||
@classmethod
|
||||
def validate_code(cls, code):
|
||||
return code in cls.id_dict if cls.item_ids is not None else False
|
||||
|
||||
def __init__(self, code, name, quantity):
|
||||
self.code = code
|
||||
self.name = name
|
||||
|
@ -106,7 +56,7 @@ class StorageArea:
|
|||
self.tag = tag
|
||||
self.type_id = None
|
||||
self.items = []
|
||||
self.is_abnormal_storage = False
|
||||
self.is_normal_storage = False
|
||||
|
||||
def add_item(self, item):
|
||||
self.items.append(item)
|
||||
|
@ -121,6 +71,58 @@ class StorageArea:
|
|||
|
||||
class Character:
|
||||
|
||||
skill_ids = None
|
||||
attribute_ids = None
|
||||
trait_ids = None
|
||||
condition_ids = None
|
||||
|
||||
@classmethod
|
||||
def load_ids(cls, skill_filename, attribute_filename, trait_filename, condition_filename):
|
||||
if cls.skill_ids is None:
|
||||
cls.skill_ids = {}
|
||||
with open(skill_filename, 'r') as skill_file:
|
||||
skill_reader = csv.reader(skill_file, delimiter='\t')
|
||||
for row in skill_reader:
|
||||
cls.skill_ids[int(row[0])] = row[1].strip()
|
||||
|
||||
if cls.attribute_ids is None:
|
||||
cls.attribute_ids = {}
|
||||
with open(attribute_filename, 'r') as attribute_file:
|
||||
attribute_reader = csv.reader(attribute_file, delimiter='\t')
|
||||
for row in attribute_reader:
|
||||
cls.attribute_ids[int(row[0])] = row[1].strip()
|
||||
|
||||
if cls.trait_ids is None:
|
||||
cls.trait_ids = {}
|
||||
with open(trait_filename, 'r') as trait_file:
|
||||
trait_reader = csv.reader(trait_file, delimiter='\t')
|
||||
for row in trait_reader:
|
||||
print(row)
|
||||
cls.trait_ids[int(row[0])] = row[1].strip()
|
||||
|
||||
if cls.condition_ids is None:
|
||||
cls.condition_ids = {}
|
||||
with open(condition_filename, 'r') as condition_file:
|
||||
condition_reader = csv.reader(condition_file, delimiter='\t')
|
||||
for row in condition_reader:
|
||||
cls.condition_ids[int(row[0])] = row[1].strip()
|
||||
|
||||
@classmethod
|
||||
def get_skill_from_code(cls, code):
|
||||
return cls.skill_ids.get(code, None) if cls.skill_ids is not None else None
|
||||
|
||||
@classmethod
|
||||
def get_attribute_from_code(cls, code):
|
||||
return cls.attribute_ids.get(code, None) if cls.attribute_ids is not None else None
|
||||
|
||||
@classmethod
|
||||
def get_trait_from_code(cls, code):
|
||||
return cls.trait_ids.get(code, None) if cls.trait_ids is not None else None
|
||||
|
||||
@classmethod
|
||||
def get_condition_from_code(cls, code):
|
||||
return cls.condition_ids.get(code, None) if cls.condition_ids is not None else None
|
||||
|
||||
def __init__(self, name, tag):
|
||||
self.name = name
|
||||
self.tag = tag
|
||||
|
@ -170,7 +172,7 @@ class Character:
|
|||
console.print()
|
||||
console.print("Skills:")
|
||||
for i, skill in enumerate(self.skills):
|
||||
row_string = "{:12} [bright_cyan]{:2}[/]".format(char_skills[skill['id']], skill['level'])
|
||||
row_string = "{:12} [bright_cyan]{:2}[/]".format(Character.get_skill_from_code(skill['id']), skill['level'])
|
||||
if i % 2 == 0:
|
||||
console.print(" [on #222222]{}[/]".format(row_string))
|
||||
else:
|
||||
|
@ -178,7 +180,7 @@ class Character:
|
|||
console.print()
|
||||
console.print("Attributes:")
|
||||
for i, attribute in enumerate(self.attributes):
|
||||
row_string = "{:12} [bright_cyan]{:2}[/]".format(char_attributes[attribute['id']], attribute['points'])
|
||||
row_string = "{:12} [bright_cyan]{:2}[/]".format(Character.get_attribute_from_code(attribute['id']), attribute['points'])
|
||||
if i % 2 == 0:
|
||||
console.print(" [on #222222]{}[/]".format(row_string))
|
||||
else:
|
||||
|
@ -206,7 +208,7 @@ class Ship:
|
|||
self.characters.append(character)
|
||||
|
||||
def add_item(self, item):
|
||||
normal_storage_areas = [sa for sa in self.storage_areas if not sa.is_abnormal_storage]
|
||||
normal_storage_areas = [sa for sa in self.storage_areas if sa.is_normal_storage]
|
||||
min_storage_area = normal_storage_areas[0]
|
||||
min_occupancy = min_storage_area.get_total_occupancy()
|
||||
for storage_area in normal_storage_areas:
|
||||
|
@ -225,12 +227,11 @@ class Player:
|
|||
|
||||
class GameData:
|
||||
|
||||
def __init__(self, soup, item_database):
|
||||
def __init__(self, soup):
|
||||
self.player = None
|
||||
self.ships = []
|
||||
|
||||
self.soup = soup
|
||||
self.item_database = item_database
|
||||
|
||||
def populate(self):
|
||||
# Step 1 - Player data
|
||||
|
@ -262,14 +263,12 @@ class GameData:
|
|||
storage_area = StorageArea(inv_tag.find('inv'))
|
||||
# 632 is the "m" id code for LARGE storage
|
||||
storage_area.type_id = int(inv_tag.parent.parent['m'])
|
||||
if storage_area.type_id not in normal_storage_ids: # TODO: Un-hardcode this AND take into account SMALL storage
|
||||
# rich.print("[on #222222]Found abnormal storage id [#666666]{}[/][/]".format(inv_tag.parent.parent['m']))
|
||||
storage_area.is_abnormal_storage = True
|
||||
storage_area.is_normal_storage = storage_area.type_id in normal_storage_ids
|
||||
ship.add_storage_area(storage_area)
|
||||
# Items within storage area
|
||||
for s_tag in inv_tag.find_all('s'):
|
||||
item_code = int(s_tag['elementaryId'])
|
||||
item_name = self.item_database.get_name_from_code(item_code)
|
||||
item_name = Item.get_name_from_code(item_code)
|
||||
item_quantity = int(s_tag['inStorage'])
|
||||
item = Item(item_code, item_name, item_quantity)
|
||||
storage_area.add_item(item)
|
||||
|
@ -420,7 +419,7 @@ class GameData:
|
|||
continue
|
||||
|
||||
for index, storage_area in enumerate(ship.storage_areas):
|
||||
console.print(" Storage area [bright_cyan]{}[/] (type: [bright_cyan]{}[/], abnormal storage: [bright_cyan]{}[/]):".format(index, storage_ids[storage_area.type_id]["name"], storage_area.is_abnormal_storage))
|
||||
console.print(" Storage area [bright_cyan]{}[/] (type: [bright_cyan]{}[/], normal storage: [bright_cyan]{}[/]):".format(index, storage_ids[storage_area.type_id]["name"], storage_area.is_normal_storage))
|
||||
if len(storage_area.items) == 0:
|
||||
console.print(" This storage area is empty.")
|
||||
console.print()
|
||||
|
@ -632,11 +631,14 @@ def main():
|
|||
|
||||
soup = BeautifulSoup(full_text, "xml")
|
||||
|
||||
item_code_database = ItemCodeDatabase('item_ids.tsv')
|
||||
Item.load_ids('item_ids.tsv')
|
||||
print("Item code database successfully loaded.")
|
||||
print()
|
||||
Character.load_ids('char_skills.tsv', 'char_attributes.tsv', 'char_traits.tsv', 'char_conditions.tsv')
|
||||
print("Character code database successfully loaded.")
|
||||
print()
|
||||
|
||||
game_data = GameData(soup, item_code_database)
|
||||
game_data = GameData(soup)
|
||||
game_data.populate()
|
||||
|
||||
edits_made = False
|
||||
|
@ -665,7 +667,7 @@ def main():
|
|||
# print(item_list)
|
||||
print("Items to be added:")
|
||||
for (item_code, item_quantity) in item_list:
|
||||
print("{} : {}".format(item_code_database.get_name_from_code(item_code), item_quantity))
|
||||
print("{} : {}".format(Item.get_name_from_code(item_code), item_quantity))
|
||||
game_data.add_item(item_code, item_quantity)
|
||||
edits_made = True
|
||||
|
||||
|
@ -678,7 +680,7 @@ def main():
|
|||
game_data.writeback()
|
||||
|
||||
if args.test_gamedata:
|
||||
game_data = GameData(soup, item_code_database)
|
||||
game_data = GameData(soup)
|
||||
game_data.populate()
|
||||
# game_data.add_item(1759, 100)
|
||||
# game_data.buff_characters()
|
||||
|
|
Loading…
Reference in New Issue