Skip to content

Commit

Permalink
Morphologies reworked to branch centric structure of arrays (#129)
Browse files Browse the repository at this point in the history
* initial write up of reworked morphologies & repo loading

* merged initial write up and TrueMorphology into Morphology class

* moved MRs that are addressed by path to test MR folder

* Removed dead code, added `flatten`

* Renamed `branches_iterator` to `branch_iter` and it uses `yield from`

* Fixed undefined `vec`

* Removed preload, turned compartments into cached property

* Added invalid branch labels checking function

* Pass scaffold to morphology from _morphology

* Catch missing branch vector datasets

* Compartments were misconstructed from 1 set of coords, added pairwise

* Bumped errr version for correct exception names during tests

* Added first batch of morphology tests

* crude seperation of Morphology from config. All vars still "morphology"

* Disabled outdated parts. Will work towards enabling arbz.

* bumped errr in requirements

* Rewrote arbz import, saving and loading of morphologies

* regenerated morphology repositories

* skip some broken tests

* Removed old storage code. Fixed some graph code errors

* Use latest dbbs_models version for PC target sets

* Added morphology labelling

* Added arborize multi-labels. closes #126

* enabled placement tests

* removed morphos.hdf5

* removed MR gitignore exception

* Started work on dynamic test MR's, "fixed" empty KDTree error

* updated main MR

* Restored connectivity

* Fixed postprocessing test

* Try dbbs bump for key error

* Added circular morphology error

* Added morpho warning

* Upgraded to patch 2.2.0 for functional SectionRef

* Added conceptual docs on morphologies

* Dynamic test files. (closes #120)

* Fixed morphology & nest tests

* Fixed entity test

* Changed rounding of step

* Fixed fiber_intersection test

* Added fixes for missing MR files

* duplicate .h5 file to top lvl, to be sure

* removed test print

* Expect an extra point at seam of branches (closes #132)

* v3.6.0b0 - Branched SoA morphologies

* Completed basic testing of morphologies.py

* Added placeholder tests
  • Loading branch information
Helveg committed Oct 7, 2020
1 parent d46c083 commit bec856d
Show file tree
Hide file tree
Showing 41 changed files with 1,078 additions and 553 deletions.
2 changes: 1 addition & 1 deletion bsb/__init__.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
__version__ = "3.5.0b1"
__version__ = "3.6.0b0"

from .reporting import set_verbosity, report, warn
4 changes: 2 additions & 2 deletions bsb/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
import os, sys, site
from inspect import isclass
from .models import CellType, Layer
from .morphologies import Morphology as BaseMorphology
from .morphologies import Representation
from .connectivity import ConnectionStrategy, FiberTransform
from .placement import PlacementStrategy
from .output import OutputFormatter, HDF5Formatter
Expand Down Expand Up @@ -666,7 +666,7 @@ def init_morphology(self, section, cell_type_name):
name = cell_type_name + "_morphology"
node_name = "cell_types.{}.morphology".format(cell_type_name)
morphology_class = assert_attr(section, "class", node_name)
morphology = load_configurable_class(name, morphology_class, BaseMorphology)
morphology = load_configurable_class(name, morphology_class, Representation)
fill_configurable_class(morphology, section, excluded=["class"])
self.add_morphology(morphology)
return morphology
Expand Down
11 changes: 4 additions & 7 deletions bsb/connectivity/connectome/glomerulus_granule.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,12 +26,8 @@ def validate(self):
)
mr = self.scaffold.morphology_repository
morphology = mr.get_morphology(morphologies[0])
dendritic_compartments = morphology.get_compartments(["dendrites"])
dendrites = {}
for c in dendritic_compartments:
# Store the last found compartment of each dendrite
dendrites[c.section_id] = c
self.dendritic_claws = [c.id for c in dendrites.values()]
branches = morphology.get_branches(["dendrites"])
self.dendritic_claws = [branch.to_compartments()[-1] for branch in branches]
self.morphology = morphology

def connect(self):
Expand Down Expand Up @@ -108,6 +104,7 @@ def connectome_glom_grc(
# Add morphology & compartment information
morpho_map = [self.morphology.morphology_name]
morphologies = np.zeros((len(connectome), 2))
# Store a map between the granule cell ids and the available claw compartments
granule_dendrite_occupation = {
g[0]: self.dendritic_claws.copy() for g in granules
}
Expand All @@ -126,7 +123,7 @@ def connectome_glom_grc(
raise ConnectivityError(
"Attempt to connect a glomerulus to a fully saturated granule cell."
)
compartments.append([0, unoccupied_claw])
compartments.append([0, unoccupied_claw.id])
self.scaffold.connect_cells(
self,
connectome,
Expand Down
21 changes: 14 additions & 7 deletions bsb/connectivity/detailed/fiber_intersection.py
Original file line number Diff line number Diff line change
Expand Up @@ -100,9 +100,7 @@ def connect(self):
for c, (from_cell, from_morpho) in enumerate(from_morphology_set):
# (1) Extract the FiberMorpho object for each branch in the from_compartments
# of the presynaptic morphology
compartments = from_morpho.get_compartments(
compartment_types=from_compartments
)
compartments = from_morpho.get_compartments(from_compartments)
morpho_rotation = from_cell.rotation
fm = FiberMorphology(compartments, morpho_rotation)

Expand Down Expand Up @@ -393,9 +391,10 @@ def transform_branch(self, branch, offset):

if not self.shared:
# Compute branch direction - to check that PFs have 2 branches, left and right
branch_dir = branch._compartments[0].end - branch._compartments[0].start
# Normalize branch_dir vector
branch_dir = branch_dir / np.linalg.norm(branch_dir)
branch_dir = self.get_branch_direction(branch)
# If the entire branch consists of compartments without direction, do nothing.
if branch_dir is False:
return

num_comp = len(branch._compartments)

Expand All @@ -409,7 +408,6 @@ def transform_branch(self, branch, offset):
# the branch direction and the original morphology/parent branch
if branch.orientation is None:
transversal_vector = np.cross(branch_dir, [0, 1, 0])
# branch.orientation =
else:
transversal_vector = np.cross(branch_dir, branch.orientation)

Expand Down Expand Up @@ -454,3 +452,12 @@ def transform_branch(self, branch, offset):
)
# The new end is the start of the adjacent compartment
branch._compartments[comp + 1].start = branch._compartments[comp].end

def get_branch_direction(self, branch):
for comp in branch._compartments:
branch_dir = comp.end - comp.start
if not np.sum(branch_dir):
continue
# Normalize branch_dir vector
branch_dir = branch_dir / np.linalg.norm(branch_dir)
return branch_dir
18 changes: 6 additions & 12 deletions bsb/connectivity/detailed/touch_detection.py
Original file line number Diff line number Diff line change
Expand Up @@ -197,25 +197,19 @@ def intersect_compartments(self, touch_info, candidate_map):
)

def get_compartment_intersections(self, touch_info, from_pos, to_pos):
from_morphology = touch_info.from_morphology
to_morphology = touch_info.to_morphology
from_morpho = touch_info.from_morphology
to_morpho = touch_info.to_morphology
query_points = (
to_morphology.get_compartment_positions(types=touch_info.to_cell_compartments)
to_morpho.get_compartment_positions(touch_info.to_cell_compartments)
+ to_pos
- from_pos
)
from_tree = from_morphology.get_compartment_tree(
compartment_types=touch_info.from_cell_compartments
)
from_tree = from_morpho.get_compartment_tree(touch_info.from_cell_compartments)
compartment_hits = from_tree.query_radius(
query_points, self.compartment_intersection_radius
)
from_map = from_morphology.get_compartment_submask(
compartment_types=touch_info.from_cell_compartments
)
to_map = to_morphology.get_compartment_submask(
compartment_types=touch_info.to_cell_compartments
)
from_map = from_morpho.get_compartment_submask(touch_info.from_cell_compartments)
to_map = to_morpho.get_compartment_submask(touch_info.to_cell_compartments)
intersections = []
for i in range(len(compartment_hits)):
hits = compartment_hits[i]
Expand Down
5 changes: 5 additions & 0 deletions bsb/exceptions.py
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@
MissingMorphologyError=_e(),
IncompleteMorphologyError=_e(),
MorphologyDataError=_e(),
CircularMorphologyError=_e("morphology", "component").set(list_details=True),
CompartmentError=_e(),
),
TreeError=_e(),
Expand Down Expand Up @@ -78,6 +79,10 @@ class PlacementWarning(ScaffoldWarning):
pass


class MorphologyWarning(ScaffoldWarning):
pass


class ConnectivityWarning(ScaffoldWarning):
pass

Expand Down
4 changes: 1 addition & 3 deletions bsb/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -632,9 +632,7 @@ def load_morpho(scaffold, morpho_ind, compartment_types=None):
self._morphology_map[morpho_ind]
)
m._set_index = morpho_ind
m.voxelize(
N, compartments=m.get_compartments(compartment_types=compartment_types)
)
m.voxelize(N, compartments=m.get_compartments(compartment_types))
return m

# Load and voxelize only the unique morphologies present in the morphology map.
Expand Down

0 comments on commit bec856d

Please sign in to comment.