def profiles_to_lattices(uniq_corner_arang, stencils):
    stencil_ind = []
    for s in stencils:
        filled_ind = np.array(np.where(np.array(s) == 1)).T
        # relocate to corner
        filled_ind_reloc = filled_ind - 1
        # flip vertically
        filled_ind_flpd = np.flip(filled_ind_reloc, 0).astype(int)

        stencil_ind.append(filled_ind_flpd)
    # print(stencil_ind)

    ######################

    # generate mini-lattices to represent the geometrical equivalent of unique corner arrangments
    base_zero = np.zeros((2, 2, 2), dtype=np.int8)

    corner_neigh_lattices = []
    corner_loc_lattices = []
    # for each unique arangement, create a representation
    for uca in uniq_corner_arang:
        corner_arang = np.copy(base_zero)
        corner_loc = np.copy(base_zero)
        corner_loc[0, 0, 0] = 1

        shift = np.zeros(3)
        # for each list of indices of each stencil
        for i, s_inds in enumerate(stencil_ind):
            # for each index
            for j, s_i in enumerate(s_inds):
                # check if the sum is big enough to mark this index
                if uca[i] > j:
                    # check if the index is positive
                    if s_i.sum() >= 0:
                        # mark as one
                        corner_arang[tuple(s_i)] = 1
                    # if the index is negative
                    else:
                        # mark as one
                        corner_arang[tuple(s_i)] = 1
                        # record the index as a shift
                        shift += s_i

        # roll neighbourhood and locations
        corner_arang = np.roll(corner_arang, tuple(shift.astype(int)),
                               (0, 1, 2))
        corner_loc = np.roll(corner_loc, tuple(shift.astype(int)), (0, 1, 2))

        # convert to lattice
        corner_lat = tg.to_lattice(corner_arang, np.zeros(3))
        corner_neigh_lattices.append(corner_lat)

        corner_loc_lat = tg.to_lattice(corner_loc, np.zeros(3))
        corner_loc_lattices.append(corner_loc_lat)

    return (corner_loc_lattices, corner_neigh_lattices)
Example #2
0
    def bhv_find_neighbour(self,
                           stencil_name: str,
                           env: environment,
                           return_counts=False,
                           return_neigh_ind=False):
        all_neighs = env.neigh_matrices[stencil_name]
        agn_neighs = all_neighs[np.where(np.array(
            self.occ_lattice).flatten())].flatten()
        neighbourhood_flat = self.occ_lattice.flatten() * 0
        # all_neighbours = env.neigh_matrix[np.where(np.array(self.occ_lattice).flatten())].reshape(tuple([-1] + list(self.occ_lattice.shape))).sum(0)
        if return_counts:
            unq_neighs, unq_counts = np.unique(agn_neighs, return_counts=True)
            neighbourhood_flat[unq_neighs] = unq_counts
        else:
            neighbourhood_flat[agn_neighs] = 1

        neighbourhood = tg.to_lattice(
            neighbourhood_flat.reshape(self.occ_lattice.shape),
            self.occ_lattice)

        if return_neigh_ind:
            if return_neigh_ind == "1D":
                indices_1d = np.argwhere(neighbourhood_flat > 0)
                return (neighbourhood, indices_1d)
            elif return_neigh_ind == "3D":
                indices_3d = np.argwhere(neighbourhood > 0)
                return (neighbourhood, indices_3d)
        else:
            return neighbourhood
Example #3
0
 def evaluation(self, env: environment):
     eval_lattice = tg.to_lattice(np.ones(env.avail_lattice.shape),
                                  env.avail_lattice.shape)
     for lat_name, lat in env.lattices.items():
         eval_lattice *= lat.astype(
             float)**self.preferences[lat_name]["weight"]
     self.eval_lat = eval_lattice
def bi_cube_lattices():
    # create all possible configurations
    l_bis = []
    for i in range(2**8):
        bi = np.array(list(np.binary_repr(i, width=8))).astype(int).reshape(
            (2, 2, 2))
        l_bi = tg.to_lattice(bi, [0, 0, 0])
        l_bis.append(l_bi)
    return l_bis
def save_design_templates(corner_loc_lattices, corner_neigh_lattices,
                          templates_path):
    interior_zero = tg.to_lattice(np.zeros((2, 2, 2), dtype=np.int8),
                                  [0, 0, 0])
    border_pad = np.pad(interior_zero, (1, 1), 'constant', constant_values=(1))
    base_zero = tg.to_lattice(np.zeros((4, 4, 4), dtype=np.int8), [0, 0, 0])
    s = tg.create_stencil("von_neumann", 1, 1)
    s.set_index([0, 0, 0], 0)

    for i, core, neigh in zip(range(len(corner_loc_lattices)),
                              corner_loc_lattices, corner_neigh_lattices):
        # construct saving paths
        core_path = os.path.join(templates_path, 'core_' + f'{i:02}' + '.csv')
        neigh_path = os.path.join(templates_path,
                                  'neighs_' + f'{i:02}' + '.csv')
        e_neigh_path = os.path.join(templates_path,
                                    'e_neighs_' + f'{i:02}' + '.csv')

        # aggregate neighbours
        neigh = tg.to_lattice(
            np.pad(neigh, (1, 1), 'constant', constant_values=(0)), [0, 0, 0])

        # construct the padded core
        core_pad = tg.to_lattice(
            np.pad(core, (1, 1), 'constant', constant_values=(0)), [0, 0, 0])
        # extract the outer neighbours of the core
        core_3ind = np.array(np.where(core_pad == 1)).flatten()
        pals = base_zero.find_neighbours_masked(s, loc=core_3ind)
        extra_neighs = np.copy(base_zero).flatten()
        # set the extra neighbours as the current state of the core
        extra_neighs[pals] = neigh[tuple(core_3ind)]
        extra_neighs = tg.to_lattice(extra_neighs.reshape((4, 4, 4)),
                                     [0, 0, 0])
        # remove interior pals
        extra_neighs *= border_pad

        # save to csv
        to_csv(core_pad, core_path)
        to_csv(neigh, neigh_path)
        to_csv(extra_neighs, e_neigh_path)
def reshape_and_store_to_lattice(values_list, envelope_lattice):
    env_all_vox_id = envelope_lattice.indices.flatten()
    env_all_vox = envelope_lattice.flatten() # envelope inclusion condition: True-False
    env_in_vox_id = env_all_vox_id[env_all_vox] # keep in-envelope voxels (True)

    # initialize array
    values_array = np.full(env_all_vox.shape, 0.0)
    
    # store values for the in-envelope voxels
    values_array[env_in_vox_id] = values_list

    # reshape to lattice shape
    values_array_3d = values_array.reshape(envelope_lattice.shape)

    # convert to lattice
    values_lattice = tg.to_lattice(values_array_3d, envelope_lattice)

    return values_lattice
def lattice_from_csv(file_path):
    # read metadata
    meta_df = pd.read_csv(file_path, nrows=3)

    shape = np.array(meta_df['shape'])
    unit = np.array(meta_df['unit'])
    minbound = np.array(meta_df['minbound'])

    # read lattice
    lattice_df = pd.read_csv(file_path, skiprows=5)
    print(lattice_df)
    # create the buffer
    buffer = np.array(lattice_df['value']).reshape(shape)

    # create the lattice
    l = tg.to_lattice(buffer, minbound=minbound, unit=unit)

    return l
        for a in self.agents:
            a.walk(self)
        # update the agent states in environment
        self.update_agents()

# construct a dummy value field
###############################

# create a series of sin values for 0 to pi
sin_a = np.sin(np.arange(lattice_size+1) / float(lattice_size) * np.pi).astype(np.float16)
# compute the outer product of the series with itself to create a radial value field
myvalue_2d_field = np.outer(sin_a,sin_a)
# add extra dimension to array to make it comaptible with lattices
myvalue_field = myvalue_2d_field[:, :, None] * sin_a[None, None, :]
# construct the lattice
myvalue_lattice = tg.to_lattice(myvalue_field, np.array([0,0,0]))


# initiate the environment
env_lattices = {"availibility": avail_lattice,
                "myvalue": myvalue_lattice}
env = environment(env_lattices, agents)

# main simulation
agent_history = []
for i in range(max_iteration):
    # print(env.availibility)
    # print(env.agent_origin)
    agn_org = [a.origin for a in env.agents]
    agent_history.append(np.array(agn_org).tolist())
    env.walk_agents()
import topogenesis as tg

lattices = []
# normalization loop
for values in lattice_values:
    # convert to numpy array
    a_values = np.array(values)

    # normalization of values
    max_values = np.max(a_values)
    min_values = np.min(a_values)
    normalized_values = (a_values - min_values) / (max_values - min_values)

    # convert to lattice
    norm_shaped_values = normalized_values.reshape(lattice_shape)
    lattice = tg.to_lattice(norm_shaped_values, np.array([0, 0, 0]))

    lattices.append(lattice)

# normalize weights
weights = np.array(lattice_weights)
weights /= np.sum(weights)
'''
 The aggregation algorithm is based on Fuzzy Logics framework that is introduced, and generalized in Pirouz Nourian dissertation: section 5.7.3, pp. 201-208, eq. 57
you can refer to it like this:

P. Nourian, “Configraphics: Graph Theoretical Methods for Design and Analysis of Spatial Configurations,” Doi.Org, vol. 6, no. 14. pp. 1–348, 2016, url. ISBN-13 15) 978-94-6186-720-9

'''
# initialize the aggregated lattice
agg_lattice = lattices[0] * 0 + 1
Example #10
0
[[[0 0 0]
  [0 1 0]
  [0 0 0]]

 [[0 1 0]
  [1 1 1]
  [0 1 0]]

 [[0 0 0]
  [0 1 0]
  [0 0 0]]]
"""

# initialize a 2d lattice with random values
r = np.random.rand(1, 5, 5)
l_vals = tg.to_lattice(r, [0, 0, 0])
"""
print(l_vals)
[[[0.5488135  0.71518937 0.60276338 0.54488318 0.4236548 ]
  [0.64589411 0.43758721 0.891773   0.96366276 0.38344152]
  [0.79172504 0.52889492 0.56804456 0.92559664 0.07103606]
  [0.0871293  0.0202184  0.83261985 0.77815675 0.87001215]
  [0.97861834 0.79915856 0.46147936 0.78052918 0.11827443]]]
"""

# initialize walkers lattice
z = np.zeros((1, 5, 5))
l_walk = tg.to_lattice(z, [0, 0, 0])
l_walk[0, 2, 2] += 1
"""
print(l_walk)