-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathsola.py
266 lines (215 loc) · 11.3 KB
/
sola.py
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
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
#!/usr/bin/env python
'''
File name: sola.py
Author: tofubridge
Description: sola reads daemon data in from a json file and writes the data
to a csv file for easier data manipulation
Python Version: 3.6.4
'''
## ========================== Import libraries =================================
import json
import csv
import os
## =========================== Useful classes ==================================
class Daemon:
'''Fields: daemon, card_desc, skill_name, skill_desc, skill_quote, summon_quote,
lb_quote, ability1_name, ability2_name, ability1_desc, ability2_desc,
daemon_type, special_bond
where all fields are Str'''
def __init__(self, daemon, card_desc=None, skill_name=None, skill_desc=None,\
skill_quote=None, summon_quote=None, lb_quote=None,\
ability1_name=None, ability2_name=None, ability1_desc=None,\
ability2_desc=None, daemon_type=None, special_bond=None):
self.daemon = daemon
self.card_desc = not_found if card_desc is None else card_desc
self.skill_name = not_found if skill_name is None else skill_name
self.skill_desc = not_found if skill_desc is None else skill_desc
self.skill_quote = not_found if skill_quote is None else skill_quote
self.summon_quote = not_found if summon_quote is None else summon_quote
self.lb_quote = not_found if lb_quote is None else lb_quote
self.ability1_name = na if ability1_name is None else ability1_name
self.ability2_name = na if ability2_name is None else ability2_name
self.ability1_desc = na if ability1_desc is None else ability1_desc
self.ability2_desc = na if ability2_desc is None else ability2_desc
self.daemon_type = not_found if daemon_type is None else daemon_type
self.special_bond = na if special_bond is None else special_bond
def __repr__(self):
display = "Name: {0}\nType: {1}\nSpecial Bond: {2}\nSkill Name: {3}\n"+\
"Ability1 Name: {4}\nAbility2 Name: {5}"
return display.format(self.daemon, self.daemon_type, self.special_bond,\
self.skill_name, self.ability1_name, self.ability2_name)
##==================== Useful constants and variables ==========================
na = "N/A"
not_found = "Not found."
ranged = "Ranged" # one of daemon_type
melee = "Melee" # one of daemon_type
healer = "Healer" # one of daemon_type
max_hp = "max HP"
skill_dmg = "skill DMG"
normal_atk = "normal ATK"
placeholder = "{#MonsterName#"
# dictionary to store all daemons from json file
daemon_dictionary = {}
## ======================== Helper function(s) =================================
# check_key(key, d) returns the value at d[key] if key is in d and None otherwise
# check_key: Str (dictof Daemon) -> (anyof Str None)
def check_key(key,d):
if key in d:
return d[key]
else:
return None
# d_type(daemons) mutates the value for each key in daemons to update the
# daemon_type field if required
# d_type: (dictof Daemon) -> (dictof Daemon)
def d_type(daemons):
for key in daemons:
dt = daemons[key].daemon_type
if max_hp in dt:
daemons[key].daemon_type = healer
elif skill_dmg in dt:
daemons[key].daemon_type = ranged
elif normal_atk in dt:
daemons[key].daemon_type = melee
else:
daemons[key].daemon_type = dt
# replacer(daemons) mutates the value for each key in daemons to update the
# special_bond, card_desc, abiity1_desc, ability2_desc field(s)
# if required
# replacer: (dictof Daemon) -> (dictof Daemon)
def replacer(daemons):
for key in daemons:
# fields to access
bond = daemons[key].special_bond
c_desc = daemons[key].card_desc
ab1_desc = daemons[key].ability1_desc
ab2_desc = daemons[key].ability2_desc
if placeholder in bond:
start = bond.find("{")
end = bond.find("}")
full_placeholder = bond[start:end+1]
daemon_id_to_replace = \
"".join(list(filter(lambda c: c.isdigit(), full_placeholder)))
daemon_id_name = daemons[daemon_id_to_replace].daemon
daemons[key].special_bond = bond.replace(full_placeholder, daemon_id_name)
else:
daemons[key].special_bond = bond
if placeholder in c_desc:
start = c_desc.find("{")
end = c_desc.find("}")
full_placeholder = c_desc[start:end+1]
daemon_id_to_replace = \
"".join(list(filter(lambda c: c.isdigit(), full_placeholder)))
daemon_id_name = daemons[daemon_id_to_replace].daemon
daemons[key].card_desc = c_desc.replace(full_placeholder, daemon_id_name)
else:
daemons[key].card_desc = c_desc
if placeholder in ab1_desc:
start = ab1_desc.find("{")
end = ab1_desc.find("}")
full_placeholder = ab1_desc[start:end+1]
daemon_id_to_replace = \
"".join(list(filter(lambda c: c.isdigit(), full_placeholder)))
daemon_id_name = daemons[daemon_id_to_replace].daemon
daemons[key].ability1_desc = ab1_desc.replace(full_placeholder, daemon_id_name)
else:
daemons[key].ability1_desc = ab1_desc
if placeholder in ab2_desc:
start = ab2_desc.find("{")
end = ab2_desc.find("}")
full_placeholder = ab2_desc[start:end+1]
daemon_id_to_replace = \
"".join(list(filter(lambda c: c.isdigit(), full_placeholder)))
daemon_id_name = daemons[daemon_id_to_replace].daemon
daemons[key].ability2_desc = ab2_desc.replace(full_placeholder, daemon_id_name)
else:
daemons[key].ability2_desc = ab2_desc
## ========================= Main Program =====================================
# ask user for the json file to read in the daemon information
user_input = input("Enter json file name: ")
# check if file actually exists or user entered faulty name
valid_input = os.path.isfile(user_input + ".json")
while valid_input == False:
print("File does not exist.")
user_input = input("Enter json file name: ")
valid_input = os.path.isfile(user_input + ".json")
# load all data in from json file, making sure encoding is correct
with open(user_input + ".json", "r", encoding="utf-8") as reader:
data = json.load(reader)
# get all necessary data from the json file
data_bundle = data["bundles"]
# get daemon id
daemon_id = sorted(data_bundle["MonsterName"]["strings"].keys())
# get daemon name, description, type
daemon_name = data_bundle["MonsterName"]["strings"]
daemon_desc = data_bundle["MonsterDesc"]["strings"]
daemon_type_bonds = data_bundle["monster_entanglement"]["strings"]
# get daemon skill info: name, description, quote
daemon_skill_name = data_bundle["MonsterSkillName"]["strings"]
daemon_skill_desc = data_bundle["MonsterSkillDesc"]["strings"]
daemon_skill_quote = data_bundle["MonsterSkillLine"]["strings"]
# get daemon ability info (there can be None, 1 and/or 2 abilities)
daemon_ability_desc = data_bundle["MonsterAbilityDesc"]["strings"]
daemon_ability_name = data_bundle["MonsterAbilityName"]["strings"]
# get daemon summon and limit break quote
daemon_summon_quote = data_bundle["MonsterFirstObtain"]["strings"]
daemon_lb_quote = data_bundle["MonsterAwakening"]["strings"]
# add daemons to daemon_dictionary
for num in daemon_id:
ab1_num = num + "01"
ab2_num = num + "02"
daemon_dictionary[num] = Daemon(daemon_name[num], check_key(num, daemon_desc),\
check_key(num, daemon_skill_name),\
check_key(num, daemon_skill_desc),\
check_key(num, daemon_skill_quote),\
check_key(num, daemon_summon_quote),\
check_key(num, daemon_lb_quote),\
check_key(ab1_num, daemon_ability_name),\
check_key(ab2_num, daemon_ability_name),\
check_key(ab1_num, daemon_ability_desc),\
check_key(ab2_num, daemon_ability_desc),\
check_key(ab1_num, daemon_type_bonds),\
check_key(ab2_num, daemon_type_bonds))
# mutate type field in daemon_dictionary to the proper daemon type if required
d_type(daemon_dictionary)
# mutate fields for each Daemon in daemon_dictionary if required
replacer(daemon_dictionary)
# ask user for file to write to
user_output = input("Enter file name to write daemon information to: ")
# check if file already exists to prevent user from overwriting that file
valid_output = os.path.isfile(user_output + ".csv")
while valid_output == True:
print("File already exists!")
user_output = input("Enter file name to write daemon information to: ")
valid_output = os.path.isfile(user_output + ".csv")
# check if filename contains forbidden characters
forbidden = ["/", "<", ">", ":", '"', "\\", "/", "|", "?", "*"]
forbidden_ending = [" ", "."]
while user_output == "" or any(i in user_output for i in forbidden) or \
user_output[-1] in forbidden_ending:
print("Yikes! That's not a friendly filename!")
user_output = input("Enter file name to write daemon information to: ")
# open a csv file for writing information from daemon_dictionary
with open(user_output + ".csv", "w", encoding="utf-8-sig") as csvfile:
# csv header values
fn = ["id","Daemon","Type", "Special Bond", "Card Desc", "LB Quote", "Summon Quote",\
"Skill Quote", "Skill Name","Skill Desc","Ability1 Name",\
"Ability1 Desc","Ability2 Name", "Ability2 Desc"]
# set up csv file and begin writing
writer = csv.DictWriter(csvfile, fieldnames=fn)
writer.writeheader()
for k in daemon_dictionary:
writer.writerow({"id": "{0}".format(k),\
"Daemon": "{0}".format(daemon_dictionary[k].daemon),\
"Type": "{0}".format(daemon_dictionary[k].daemon_type),\
"Special Bond": "{0}".format(daemon_dictionary[k].special_bond),\
"Card Desc": "{0}".format(daemon_dictionary[k].card_desc),\
"LB Quote": "{0}".format(daemon_dictionary[k].lb_quote),\
"Summon Quote": "{0}".format(daemon_dictionary[k].summon_quote),\
"Skill Quote": "{0}".format(daemon_dictionary[k].skill_quote),\
"Skill Name": "{0}".format(daemon_dictionary[k].skill_name),\
"Skill Desc": "{0}".format(daemon_dictionary[k].skill_desc),\
"Ability1 Name": "{0}".format(daemon_dictionary[k].ability1_name),\
"Ability1 Desc": "{0}".format(daemon_dictionary[k].ability1_desc),\
"Ability2 Name": "{0}".format(daemon_dictionary[k].ability2_name),\
"Ability2 Desc": "{0}".format(daemon_dictionary[k].ability2_desc),})
print("sola has finished writing to '{0}'".format(user_output+".csv"))