def make_capital_county(c_size=5, origin=Cube(), coastal=True, rgb=None): '''Makes a county where all provinces neighbor the central province.''' rgb = rgb or c_col() a = Tile(origin=origin, rgb=rgb) cube_list = list(Cube(0, 0, 0).neighbors()) if coastal and c_size < 7: a.water_list.append(cube_list[c_size - 1]) cube_list = cube_list[:c_size - 1] for el in cube_list: a.add_hex(el) return a
def make_island_kingdom(water_height, origin=None, size_list=[6, 4, 4, 3], banned=[], weighted=True, min_mag=6, min_capital_coast=3, min_coast=2, max_tries=1000, strait_prob=0.5, center_bias=0.5, coast_bias=0.125): '''Given a dictionary from cubes to distance from shore, return a tile with duchies whose size are from duchy_size_list, and which are connected either directly or by straits (with probability strait_prob), and doesn't have any hexes in banned. The probability that a hex is selected as the origin is proportional to np.exp(-el.mag() * center_bias) * np.exp(water_height[el] * coast_bias), so high values of center_bias will make it closer to the center and high values of coast_bias will make it further from the shore. Tries max_tries times and returns False if it fails.''' assert min_capital_coast >= 3 assert min_coast >= 2 for _ in range(max_tries): island = Tile(hex_list=[], tile_list=[make_capital_duchy(d_size=size_list[0])]) if origin: island.tile_list[0].origin = origin else: opts = [ k for k, v in water_height.items() if v >= min_capital_coast and k.mag() >= min_mag ] #center-coast-water-land means center has to be at least 3. probs = [ np.exp(-el.mag() * center_bias) * np.exp(water_height[el] * coast_bias) for el in opts ] probs /= sum(probs) island.tile_list[0].origin = np.random.choice(opts, p=probs) allowable = [ k for k, v in water_height.items() if v >= min_coast and k not in banned ] if any([el not in allowable for el in island.real_hex_list()]): break for size in size_list[1:]: allocated = island.real_total_list() land_nbrs = island.neighbors() allowable = [el for el in allowable if el not in allocated] if np.random.rand() <= strait_prob: opts = [ el for el in island.strait_neighbors() if el in allowable ] new_origin = random.choice(opts) water_hexes = set() new_origin_nbrs = new_origin.neighbors() land = island.real_hex_list() for strait_neighbor in new_origin.strait_neighbors(): if strait_neighbor in land: water_hexes.update([ el for el in strait_neighbor.neighbors() if el in new_origin_nbrs ]) new_tile = Tile(hex_list=[new_origin], water_list=list(water_hexes)) while len(new_tile.hex_list) < size: new_neighbors = new_tile.relative_neighbors(weighted) new_neighbors = [ x for x in new_neighbors if x not in land_nbrs and x in allowable ] if len(new_neighbors) > 0: new_tile.add_hex(random.choice(new_neighbors)) else: break if len(new_tile.hex_list) == size: island.add_tile(new_tile) else: opts = [el for el in island.neighbors() if el in allowable] new_origin = random.choice(opts) new_tile = Tile(hex_list=[new_origin]) while len(new_tile.hex_list) < size: new_neighbors = new_tile.relative_neighbors(weighted) new_neighbors = [ x for x in new_neighbors if x not in allocated and x in allowable ] if len(new_neighbors) > 0: new_tile.add_hex(random.choice(new_neighbors)) else: break if len(new_tile.hex_list) == size: island.add_tile(new_tile) if len(island.real_hex_list()) == sum( size_list) and check_water_access( island.real_hex_list(), island.real_water_list(), max([el.mag() for el in island.real_hex_list()])): return island return False