forked from LazoVelko/Pokemon-Terminal
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathdatabase.py
More file actions
244 lines (206 loc) · 8.93 KB
/
Copy pathdatabase.py
File metadata and controls
244 lines (206 loc) · 8.93 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
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
# The Database object is a container for all the supported Pokemon.
import os
import random
class Pokemon:
__id = "" # ID is stored as a string because it must maintain "003" format, not "3".
__name = ""
__region = ""
__path = "" # The location of the image.
def __init__(self, identifier, name, region, path):
self.__id = identifier
self.__name = name
self.__region = region
self.__path = path
def get_id(self):
if self.is_extra():
return "---" # Pokemon from folder 'Extra' have no ID.
else:
return self.__id
def get_name(self):
return self.__name
def get_region(self):
return self.__region
def get_path(self):
return self.__path
def is_extra(self):
return self.__id is None
def __str__(self):
if self.is_extra():
return "--- " + self.get_name().capitalize() + " at " + self.get_path()
else:
return self.get_id() + " " + self.get_name().capitalize() + " at " + self.get_path()
class Database:
__pokemon_list = []
__pokemon_dictionary = {}
__directory = "" # The global location of the code.
__MAX_ID = 493 # Highest possible Pokemon ID.
__regions = ('kanto', 'johto', 'hoenn', 'sinnoh')
def __init__(self):
self.directory = os.path.dirname(os.path.realpath(__file__))
self.__load_data()
self.__load_extra()
def __str__(self):
string = ""
for element in self.__pokemon_list:
string += str(element) + "\n"
return string[:-1] # Remove the final new line ("\n").
def __contains__(self, pokemon):
# Check for a Pokemon by ID or name.
if type(pokemon) is int or str(pokemon).isdigit():
return self.pokemon_id_exists(pokemon)
else:
return self.pokemon_name_exists(pokemon)
def __len__(self):
return len(self.__pokemon_list)
def get_all(self):
# Get all the Pokemon.
result = []
for pokemon in self.__pokemon_list:
result.append(pokemon)
return result
def get_regions(self):
# Get all the supported regions.
return self.__regions
def get_kanto(self):
# Get all the Pokemon from the Kanto region.
return self.__get_region("kanto")
def get_johto(self):
# Get all the Pokemon from the Johto region.
return self.__get_region("johto")
def get_hoenn(self):
# Get all the Pokemon from the Hoenn region.
return self.__get_region("hoenn")
def get_sinnoh(self):
# Get all the Pokemon from the Sinnoh region.
return self.__get_region("sinnoh")
def get_extra(self):
# Get all the Extra Pokemon images available.
return self.__get_region(None)
def __get_region(self, region):
# Helper method for getting all the Pokemon of a specified region.
result = []
for pokemon in self.__pokemon_list:
if pokemon.get_region() == region:
result.append(pokemon)
return result
def get_random(self):
# Select a random Pokemon from the database.
random_int = random.randint(0, len(self.__pokemon_list) - 1)
return self.__pokemon_list[random_int]
def get_random_from_region(self, region):
# Get a random Pokemon from a specific region.
region_pokemon = self.__get_region(region)
random_int = random.randint(0, len(region_pokemon) - 1)
return region_pokemon[random_int]
def pokemon_id_exists(self, identifier):
# Check for Pokemon by ID.
identifier = int(identifier)
if identifier < 1 or identifier > self.__MAX_ID:
return False
else:
return True
def pokemon_name_exists(self, name):
# Check for Pokemon by Name.
return name.lower() in self.__pokemon_dictionary
def get_pokemon(self, pokemon):
# Get a Pokemon by name or ID.
if type(pokemon) is not int and type(pokemon) is not str:
raise Exception("The parameter Pokemon must be of type integer or string.")
if not self.__contains__(pokemon):
raise Exception("No such Pokemon in the database.")
if type(pokemon) is int or str(pokemon).isdigit():
return self.get_pokemon_by_id(pokemon)
else:
return self.get_pokemon_by_name(pokemon)
def get_pokemon_by_name(self, name):
# Get a Pokemon by its name.
if type(name) is not str:
raise TypeError("The type of name must be a string.")
if not self.pokemon_name_exists(name):
raise Exception("No such Pokemon in the database.")
return self.__pokemon_dictionary[name]
def get_pokemon_by_id(self, identifier):
# Get a Pokemon by its ID.
if type(identifier) is not int and not str(identifier).isdigit():
raise TypeError("The Pokemon ID must be a number.")
if not self.pokemon_id_exists(identifier):
raise Exception("The Pokemon ID must be between 1 and " + str(self.__MAX_ID) + " inclusive.")
return self.__pokemon_list[int(identifier) - 1] # Subtract 1 to convert to 0 base indexing.
def names_with_prefix(self, prefix):
# Return Pokemon who's names begin with the specified prefix.
result = []
for pokemon in self.__pokemon_list:
if str(pokemon.get_name()).startswith(prefix):
result.append(pokemon)
return result
def names_with_infix(self, infix):
# Return Pokemon who's names contains the specified infix.
result = []
for pokemon in self.__pokemon_list:
if infix in str(pokemon.get_name()):
result.append(pokemon)
return result
def __load_data(self):
# Load all the Pokemon data. This does not include the 'Extra' Pokemon.
path = "/./Data/pokemon.txt"
data_file = open(self.directory + path, 'r')
for line in data_file: # Load everything but the Pokemon from the 'Extra' folder.
identifier = line.split(' ')[0] # First part of the line is the id.
name = line[len(identifier)+1:-1].lower() # The rest is the name (minus the new line at the end).
identifier = self.__add_zeroes(identifier) # This statement cannot occur before name has been created.
region = self.__determine_region(identifier)
path = self.__determine_folder(identifier) + "/" + identifier + ".png"
pokemon = Pokemon(identifier, name, region, path)
self.__pokemon_list.append(pokemon)
self.__pokemon_dictionary[pokemon.get_name()] = pokemon
def __load_extra(self):
# Load all the file names of the images in the Extra folder.
for file in os.listdir(self.directory + "/./Images/Extra"):
if file.endswith(".png"):
name = os.path.join("/Images/Extra", file).split('/')[-1][0:-4].lower()
path = self.directory + "/./Images/Extra/" + name + ".png"
pokemon = Pokemon(None, name, None, path)
if name in self.__pokemon_dictionary:
raise Exception("Duplicate names detected. "
"The name of the file " + str(name) + ".png in the folder 'Extra' must be changed.")
self.__pokemon_list.append(pokemon)
self.__pokemon_dictionary[pokemon.get_name()] = pokemon
@staticmethod
def __add_zeroes(number):
# Add zeroes to the front so that it begins with 3 digits. Example: "2" -> "002".
zeroes = ""
if int(number) < 10:
zeroes = "00"
elif int(number) < 100:
zeroes = "0"
return zeroes + str(number)
def __determine_region(self, identifier):
# Determine which region a Pokemon is from.
identifier = int(identifier)
if identifier < 1:
raise Exception("Pokemon ID cannot be less than 1.")
if identifier < 152:
return "kanto"
elif identifier < 252:
return "johto"
elif identifier < 387:
return "hoenn"
elif identifier < 494:
return "sinnoh"
else:
raise Exception("Pokemon ID cannot be greater than 493.")
def __determine_folder(self, identifier):
# Determine which folder a Pokemon is from.
identifier = int(identifier)
if identifier < 1:
raise Exception("Pokemon ID cannot be less than 1.")
if identifier < 152:
return self.directory + "/./Images/Generation I - Kanto"
elif identifier < 252:
return self.directory + "/./Images/Generation II - Johto"
elif identifier < 387:
return self.directory + "/./Images/Generation III - Hoenn"
elif identifier < 494:
return self.directory + "/./Images/Generation IV - Sinnoh"
else:
raise Exception("Pokemon ID cannot be greater than 493.")