Skip to content

Commit

Permalink
Added html to base (Dayum)
Browse files Browse the repository at this point in the history
Lots of other important changes that I cant remember
  • Loading branch information
Royz2123 authored and Royz2123 committed May 27, 2019
1 parent c6bf941 commit 4f53a04
Show file tree
Hide file tree
Showing 22 changed files with 787 additions and 244 deletions.
49 changes: 30 additions & 19 deletions army_genetics.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
import util

MAIN_BOARD = generate_base.generate_main_base()

SAVE_FOLDER = "./optimize_viz/"

class ArmyGenetics:
"""
Expand Down Expand Up @@ -42,34 +42,45 @@ def run(self):
"""

def calc_fitness(self):
outcome = self.run()

# calculate fitness
if self._mode == REGULAR:
self._fit = 2 * outcome["percent"] + 0.3 * outcome["stars"] + outcome["gold"] + outcome["elixir"]
elif self._mode == DESTORYER:
self._fit = 2 * outcome["percent"] + 0.3 * outcome["stars"]
elif self._mode == GOLD_DIGGER:
self._fit = outcome["gold"]
elif self._mode == ELIXIR_LOVER:
self._fit = outcome["elixir"]
elif self._mode == GOLD_DIGGER:
self._fit = outcome["gold"] + outcome["elixir"]
try:
outcome = self.run()

# calculate fitness
if self._mode == REGULAR:
self._fit = 2 * outcome["percent"] + 0.3 * outcome["stars"] + outcome["gold"] + outcome["elixir"]
elif self._mode == DESTORYER:
self._fit = 2 * outcome["percent"] + 0.3 * outcome["stars"]
elif self._mode == GOLD_DIGGER:
self._fit = outcome["gold"]
elif self._mode == ELIXIR_LOVER:
self._fit = outcome["elixir"]
elif self._mode == GOLD_DIGGER:
self._fit = outcome["gold"] + outcome["elixir"]

except Exception as e:
print(e)
self._fit = 0

print(self._fit)

def get_fitness(self):
return self._fit

def viz(self):
board_viz.viz_board(game_board=self._game_board, army=self._army, viz=True)

def viz(self, index, viz_mode=True):
if viz_mode:
path = SAVE_FOLDER + "%04d.png" % index
board_viz.viz_board(game_board=self._game_board, army=self._army, viz=False, path=path)

"""
Our mutation function.
"""

def mutation(self):
print("Mutating Army!")
self.mutation2()
# Large change or small change
if random.randint(0, 1):
self.mutation2()
else:
self.mutation1(MUTATION_RATE)

def mutation2(self):
self._army[random.randint(0, len(self._army) - 1)].set_pos(util.gen_location())
Expand Down
47 changes: 40 additions & 7 deletions base_from_html.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,21 +3,54 @@
import board

def get_html(html_file = board.GameBoard.HTML_FILE):
with open(board.GameBoard.HTML_FILE, "r") as f:
with open(html_file, "r") as f:
return f.read()


def to_buildings():
html_doc = get_html()
def html_to_game_board(html_file="bases/base1.html", viz=True):
html_doc = get_html(html_file)

soup = BeautifulSoup(html_doc, 'html.parser')
buildings = soup.find(id="grid").children
buildings = soup.find_all("div", class_=["coc-b", "wall"])

building_infos = []
for b in buildings:
try:
print(b["style"])
except:
pass
# get level and class
if b["class"][0] == "wall":
class_str = "wall"
level = int(b["class"][1][3:])
else:
class_str = b["class"][1].split('-')[1]
level = int(b["class"][2][3:])

# get position
pos = b["style"].split("px")[:2]
pos = tuple([int(coord.split(" ")[-1]) // 20 for coord in pos])

# create object from said parameters
if class_str in board.BUILDINGS_MAP_NAME.keys():
building_infos.append((class_str, level, pos))

except Exception as e:
print(e)

# set all positions to align to (0, 0)
min_x = min(building_infos, key=lambda x: x[2][0])[2][0]
min_y = min(building_infos, key=lambda x: x[2][1])[2][1]
building_infos = [(c, l, (p[0] - min_x, p[1] - min_y)) for c, l, p in building_infos]

# create objects
building_objs = []
for class_str, level, pos in building_infos:
building_objs.append(board.create_obj_from_name(class_str)(level=level, pos=pos))

# visualize if necessary
if viz:
gb = board.GameBoard(building_objs)
gb.update_viz()
return building_objs


if __name__ == "__main__":
to_buildings()
495 changes: 495 additions & 0 deletions bases/base1.html

Large diffs are not rendered by default.

25 changes: 24 additions & 1 deletion board.py
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,24 @@
Wall: 14
}

BUILDINGS_MAP_NAME = {
"empty" : Empty,
"cannon" : Cannon,
"archer" : ArcherTower,
"townhall" : TownHall,
"labratory": Labratory,
"mortar": Mortar,
"builder": Builder,
"elixerstorage": ElixirStorage,
"goldstorage": GoldStorage,
"gold": GoldCollector,
"elixer": ElixirCollector,
"barracks": Barracks,
"castle": ClanCastle,
"army": ArmyCamps,
"wall": Wall
}


def create_obj_from_index(search_index):
for obj, index in BUILDINGS_MAP.items():
Expand All @@ -32,6 +50,11 @@ def create_obj_from_index(search_index):
return None


def create_obj_from_name(name):
if name in BUILDINGS_MAP_NAME.keys():
return BUILDINGS_MAP_NAME[name]
return None


OBJECTS = [create_obj_from_index(i)(pos=(0, 0), level=1) for i in range(len(QUANTS))]

Expand All @@ -47,7 +70,7 @@ class GameBoard(object):
"""

def create_buildings(quants, levels):
return generate_board.generate_random_base(quants, levels)
return generate_base.generate_random_base(quants, levels)

DEFAULT_BASE = [Cannon((1, 0))]

Expand Down
2 changes: 1 addition & 1 deletion board_genetics.py
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ def calc_fitness(self):
def get_fitness(self):
return self._fit

def viz(self):
def viz(self, index):
self.game_board.update_viz()

"""
Expand Down
10 changes: 9 additions & 1 deletion board_viz.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,22 @@

from constants import *
from buildings import *
import simulator
import generate_base
import generate_army

from mpl_toolkits.mplot3d import Axes3D
import matplotlib.pyplot as plt
from matplotlib import cm
from matplotlib.ticker import LinearLocator, FormatStrFormatter
import numpy as np

from constants import *
import os
import cv2

MAIN_BOARD = generate_base.generate_main_base()


def draw_list(lst, color='r'):
for (x, y) in lst:
Expand Down Expand Up @@ -104,4 +113,3 @@ def create_video(path):
cv2.destroyAllWindows()



12 changes: 12 additions & 0 deletions generate_army.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,3 +37,15 @@ def generate_army_from_row(row, quants=DEFAULT_QUANTS, levels=DEFAULT_LEVELS):
army.append(TROOPS[i](pos=(x, y), level=levels[i]))
curr_index += 2
return army


# Generate a single super barb at every spot
def generate_barb_matrix():
armies = []
for x in range(-MARGIN, BOARD_SIZE + MARGIN):
for y in range(-MARGIN, BOARD_SIZE + MARGIN):
if util.in_margins((x, y)):
super_troop = Barbarian((x, y))
super_troop.set_hp(1000)
armies.append([super_troop])
return armies
40 changes: 39 additions & 1 deletion main.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,43 @@
import generate_army
import board_viz

from constants import *

from mpl_toolkits.mplot3d import Axes3D
import matplotlib.pyplot as plt
from matplotlib import cm
from matplotlib.ticker import LinearLocator, FormatStrFormatter
import numpy as np

MAIN_BOARD = generate_base.generate_main_base()


def plot_single_barb_mat(armies):
# Make data.
X = []
Y = []
Z = []

gb = board.GameBoard(generate_base.generate_main_base())
sim = simulator.Simulator(gb)

for army in armies:
stats = sim.run(army)
x, y = army[0].get_pos()

X.append(x)
Y.append(y)
Z.append(stats["percent"])

# plot 3d
fig = plt.figure()
ax = fig.gca(projection='3d')

# Plot the surface.
surf = ax.scatter(X, Y, Z, cmap=cm.coolwarm,
linewidth=0, antialiased=False)
plt.show()


def main():
gb = board.GameBoard(generate_base.generate_main_base())
Expand All @@ -20,4 +57,5 @@ def main():


if __name__ == "__main__":
main()
plot_single_barb_mat(generate_army.generate_barb_matrix())
#main()
Binary file added optimize_viz/0001.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added optimize_viz/0002.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added optimize_viz/0003.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added optimize_viz/0004.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added optimize_viz/0005.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added optimize_viz/0006.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added optimize_viz/0007.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added optimize_viz/0008.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
27 changes: 20 additions & 7 deletions pyeasyga/pyeasyga.py
Original file line number Diff line number Diff line change
Expand Up @@ -200,16 +200,29 @@ def create_next_generation(self,gen):
def run(self):
"""Run (solve) the Genetic Algorithm."""
best_fitness = []
best_individuals = []

self.create_first_generation()
print("Population created!")
for _ in range(1, self.generations):
self.best_individual()[1].viz()
best_fitness.append(self.best_individual()[0])
print("Best fitness: " + str(self.best_individual()[0]))
for index in range(1, self.generations):
best_individual = self.best_individual()

# visualize best individual
best_individual[1].viz(index)

# save best individuals
best_fitness.append(best_individual[0])
best_individuals.append(best_individual[1])

# debug
print("Generation " + str(index) + " completed!")
print("Best fitness: " + str(best_individual[0]))
print("Overall improvement: " + str(best_fitness))
print("Generation " + str(_) + " completed!")
self.create_next_generation(_)
print("All done!")

# next iteration
self.create_next_generation(index)

return best_fitness, best_individuals

def best_individual(self):
"""Return the individual with the best fitness in the current
Expand Down
6 changes: 2 additions & 4 deletions run_genetics.py
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ def fitness(individual, data):
def main(option="army"):
genetic_alg = ps.GeneticAlgorithm(
option,
population_size=50,
population_size=20,
generations=200,
mutation_probability=MUTATION_RATE,
elitism=True,
Expand All @@ -55,9 +55,7 @@ def main(option="army"):
genetic_alg.fitness_function = fitness
genetic_alg.mutate_function = mutate
genetic_alg.crossover_function = crossover
genetic_alg.run()

genetic_alg.best_individual()[1].game_board.update_viz()
best_fitness, best_individuals = genetic_alg.run()


if __name__ == "__main__":
Expand Down
Loading

0 comments on commit 4f53a04

Please sign in to comment.