From 14a47536d61b44d10f706dfc805ccc3fc3c8bddd Mon Sep 17 00:00:00 2001 From: Kenichi Maeda Date: Thu, 15 Aug 2024 08:55:26 +0200 Subject: [PATCH] implement set_hp_flag function --- ...BrainVerciseMesh_AdaptiveMeshRefinement.py | 6 +++- ossdbs/api.py | 36 +++++-------------- ossdbs/electrodes/electrode_model_template.py | 22 ++++++++++++ .../volume_conductor_model.py | 7 ++-- ossdbs/utils/settings.py | 6 +++- 5 files changed, 44 insertions(+), 33 deletions(-) diff --git a/examples/MeshAPI/BrainVerciseMesh_AdaptiveMeshRefinement.py b/examples/MeshAPI/BrainVerciseMesh_AdaptiveMeshRefinement.py index 761b3785..99966d58 100644 --- a/examples/MeshAPI/BrainVerciseMesh_AdaptiveMeshRefinement.py +++ b/examples/MeshAPI/BrainVerciseMesh_AdaptiveMeshRefinement.py @@ -57,7 +57,11 @@ ], "MaterialDistribution": {"MRIPath": "../../input_files/Butenko_segmask.nii.gz"}, "Mesh": { - "AdaptiveMeshRefinement": {"Active": True, "MaxIterations": 2}, + "AdaptiveMeshRefinement": { + "Active": True, + "MaxIterations": 2, + "ErrorTolerance": 0.1, + }, "HPRefinement": {"Active": False, "Order": 1}, }, "StimulationSignal": { diff --git a/ossdbs/api.py b/ossdbs/api.py index 9fcd7c56..6fdc3a3a 100644 --- a/ossdbs/api.py +++ b/ossdbs/api.py @@ -15,7 +15,6 @@ dielectric_models, ) from ossdbs.electrodes import ELECTRODE_MODELS, ELECTRODE_PARAMETERS, ELECTRODES -from ossdbs.electrodes.electrode_model_template import ElectrodeModel from ossdbs.fem import ( PRECONDITIONERS, SOLVERS, @@ -60,6 +59,10 @@ def create_bounding_box(box_parameters: dict) -> BoundingBox: def generate_electrodes(settings: dict): """Generate an OCC electrode model from the settings dict.""" _logger.info("Generate electrode geometries") + + hp_refinement = False + if "HPRefinement" in settings["Mesh"]: + hp_refinement = settings["Mesh"]["HPRefinement"]["Active"] electrodes = [] for electrode_parameters in settings["Electrodes"]: name = electrode_parameters["Name"] @@ -95,18 +98,11 @@ def generate_electrodes(settings: dict): rotation=rotation, ) - # Apply hp-refinement only on active contacts - if "HPRefinement" in settings["Mesh"]: - hp_settings = settings["Mesh"]["HPRefinement"] - if hp_settings["Active"] and "Contacts" in electrode_parameters: - for contact_info in electrode_parameters["Contacts"]: - if contact_info["Active"]: - contact_idx = contact_info["Contact_ID"] - order = hp_settings["Order"] - _set_edge_hp_flag(electrode, {f"Contact_{contact_idx}": order}) - _set_vertex_hp_flag( - electrode, {f"Contact_{contact_idx}": order} - ) + if hp_refinement: + electrode.set_hp_flag( + electrode_parameters=electrode_parameters, + hp_parameters=settings["Mesh"]["HPRefinement"], + ) if "EncapsulationLayer" in electrode_parameters: electrode.encapsulation_thickness = electrode_parameters[ @@ -631,17 +627,3 @@ def run_PAM(settings): scaling=settings["Scaling"], scaling_index=settings["ScalingIndex"], ) - - -def _set_edge_hp_flag(electrode: ElectrodeModel, edge_sizes: dict) -> None: - """Set flag on edges.""" - for edge in electrode.geometry.edges: - if edge.name in edge_sizes: - edge.hpref = edge_sizes[edge.name] - - -def _set_vertex_hp_flag(electrode: ElectrodeModel, vertex_sizes) -> None: - """Set flag on vertices.""" - for vertex in electrode.geometry.vertices: - if vertex.name in vertex_sizes: - vertex.hpref = vertex_sizes[vertex.name] diff --git a/ossdbs/electrodes/electrode_model_template.py b/ossdbs/electrodes/electrode_model_template.py index 88d4a62a..70df80e9 100644 --- a/ossdbs/electrodes/electrode_model_template.py +++ b/ossdbs/electrodes/electrode_model_template.py @@ -225,3 +225,25 @@ def export_electrode(self, output_path, brain_dict, n_electrode) -> None: filename=f"{output_path}/electrode_{n_electrode}", subdivision=0, ).Do(vb=BND) + + def set_hp_flag(self, electrode_parameters: dict, hp_parameters: dict): + """Set hp-flags only on active contacts.""" + if "Contacts" in electrode_parameters: + for contact_info in electrode_parameters["Contacts"]: + if contact_info["Active"]: + contact_idx = contact_info["Contact_ID"] + order = hp_parameters["Order"] + self._set_edge_hp_flag({f"Contact_{contact_idx}": order}) + self._set_vertex_hp_flag({f"Contact_{contact_idx}": order}) + + def _set_edge_hp_flag(self, edge_sizes: dict) -> None: + """Set flags on edges.""" + for edge in self.geometry.edges: + if edge.name in edge_sizes: + edge.hpref = edge_sizes[edge.name] + + def _set_vertex_hp_flag(self, vertex_sizes) -> None: + """Set flags on vertices.""" + for vertex in self.geometry.vertices: + if vertex.name in vertex_sizes: + vertex.hpref = vertex_sizes[vertex.name] diff --git a/ossdbs/fem/volume_conductor/volume_conductor_model.py b/ossdbs/fem/volume_conductor/volume_conductor_model.py index 02190eb7..59041f79 100644 --- a/ossdbs/fem/volume_conductor/volume_conductor_model.py +++ b/ossdbs/fem/volume_conductor/volume_conductor_model.py @@ -260,11 +260,10 @@ def run_full_analysis( # currently: refine until impedance doesn't change by more than 0.1% error = 100 refinements = 0 + tolerance = adaptive_mesh_refinement["ErrorTolerance"] + max_iterations = adaptive_mesh_refinement["MaxIterations"] # TODO write a meaningful algo - while ( - error > 0.1 - and refinements < adaptive_mesh_refinement["MaxIterations"] - ): + while error > tolerance and refinements < max_iterations: self.adaptive_mesh_refinement() # solve on refined mesh self.compute_solution(frequency) diff --git a/ossdbs/utils/settings.py b/ossdbs/utils/settings.py index 4b67a8bb..e0517397 100644 --- a/ossdbs/utils/settings.py +++ b/ossdbs/utils/settings.py @@ -65,7 +65,11 @@ class Settings: "MaxMeshSize": 1e6, }, "HPRefinement": {"Active": False, "Order": 1}, - "AdaptiveMeshRefinement": {"Active": False, "MaxIterations": 10}, + "AdaptiveMeshRefinement": { + "Active": False, + "MaxIterations": 10, + "ErrorTolerance": 0.1, + }, "MeshSize": {"Edges": {}, "Faces": {}, "Volumes": {}}, "SaveMesh": False, "SavePath": "mesh",