diff --git a/mapclientplugins/scaffoldcreator/model/scaffoldcreatormodel.py b/mapclientplugins/scaffoldcreator/model/scaffoldcreatormodel.py
index bf7ab46..fa742e5 100644
--- a/mapclientplugins/scaffoldcreator/model/scaffoldcreatormodel.py
+++ b/mapclientplugins/scaffoldcreator/model/scaffoldcreatormodel.py
@@ -8,7 +8,7 @@
from cmlibs.utils.zinc.general import ChangeManager, HierarchicalChangeManager
from cmlibs.utils.zinc.group import group_add_group_elements, group_get_highest_dimension, \
identifier_ranges_fix, identifier_ranges_from_string, identifier_ranges_to_string, mesh_group_to_identifier_ranges
-from cmlibs.utils.zinc.region import determine_appropriate_glyph_size
+from cmlibs.utils.zinc.region import determine_appropriate_glyph_size, copy_fitting_data
from cmlibs.utils.zinc.scene import (
scene_create_selection_group, scene_get_selection_group, scene_create_node_derivative_graphics)
from cmlibs.zinc.field import Field, FieldGroup
@@ -18,8 +18,11 @@
from scaffoldmaker.annotation.annotationgroup import findAnnotationGroupByName, getAnnotationMarkerGroup, \
getAnnotationMarkerLocationField, getAnnotationMarkerNameField
from scaffoldmaker.scaffolds import Scaffolds
+from scaffoldmaker.utils.zinc_utils import find_or_create_field_zero_fibres
from scaffoldmaker.scaffoldpackage import ScaffoldPackage
from scaffoldmaker.utils.exportvtk import ExportVtk
+from scaffoldfitter.fitter import Fitter as GeometryFitter
+from scaffoldfitter.fitterstepalign import FitterStepAlign
import copy
import math
@@ -734,6 +737,65 @@ def applyTransformation(self, editCoordinatesField):
self._checkCustomParameterSet()
self._setGraphicsTransformation()
+ def initializeAutoAlignTransformation(self):
+ """
+ Initialize the fitter for the automatic align process
+ """
+ scaffold_region = self._region
+ # Load data into the current region (copied from load_vagus_data in 3d_nerve1)
+ # This way of loading data is probably not completely right? Need to consult for a better way
+ data_region = self._parentRegion.findChildByName('data')
+ data_fieldmodule = data_region.getFieldmodule()
+ with ChangeManager(data_fieldmodule):
+ copy_fitting_data(scaffold_region, data_region)
+ del data_region, data_fieldmodule
+ # Setup fitting routine
+ fieldmodule = scaffold_region.getFieldmodule()
+ self.fitter = GeometryFitter(region=scaffold_region)
+ self.fitter.getInitialFitterStepConfig()
+ # Load the _loadModel routines
+ self.fitter._discoverModelCoordinatesField()
+ self.fitter._discoverModelFitGroup()
+ zero_fibres = find_or_create_field_zero_fibres(fieldmodule)
+ self.fitter.setFibreField(zero_fibres)
+ del zero_fibres
+ self.fitter._discoverFlattenGroup()
+ self.fitter.defineCommonMeshFields()
+ # Load the _loadData routines
+ self.fitter._discoverDataCoordinatesField()
+ self.fitter._discoverMarkerGroup()
+ self.fitter.defineDataProjectionFields()
+ # Start fit
+ self.fitter.initializeFit()
+ fit1 = FitterStepAlign()
+ self.fitter.addFitterStep(fit1)
+ return fit1.canAutoAlign()
+
+ def runAutoAlignTransformation(self):
+ """
+ Run the align step and update visual settings
+ """
+ scaffoldPackage = self._scaffoldPackages[-1]
+ fit1 = self.fitter.getFitterSteps()[-1]
+ # Add markers/groups to align step if possible
+ if fit1.canAlignMarkers():
+ fit1.setAlignMarkers(True)
+ if fit1.canAlignGroups():
+ fit1.setAlignGroups(True)
+ # Run align step
+ fit1._doAutoAlign()
+ # Store align rotation settings
+ rotation = [rad * 180.0 / math.pi for rad in fit1._rotation]
+ scale = [fit1._scale for i in range(3)]
+ translation = fit1._translation
+ del fit1
+ # If any visual settings changes, update graphics settings
+ update_rotation = scaffoldPackage.setRotation(rotation)
+ update_scale = scaffoldPackage.setScale(scale)
+ update_translation = scaffoldPackage.setTranslation(translation)
+ if update_rotation or update_scale or update_translation:
+ self._setGraphicsTransformation()
+
def getRotationText(self):
return ', '.join(STRING_FLOAT_FORMAT.format(value) for value in self._scaffoldPackages[-1].getRotation())
diff --git a/mapclientplugins/scaffoldcreator/qt/scaffoldsettingswidget.ui b/mapclientplugins/scaffoldcreator/qt/scaffoldsettingswidget.ui
index e1f1dae..50657af 100644
--- a/mapclientplugins/scaffoldcreator/qt/scaffoldsettingswidget.ui
+++ b/mapclientplugins/scaffoldcreator/qt/scaffoldsettingswidget.ui
@@ -6,7 +6,7 @@
0
0
- 556
+ 554
773
@@ -41,7 +41,7 @@
- QFrame::NoFrame
+ QFrame::Shape::NoFrame
-
@@ -56,7 +56,7 @@
-
- Qt::Horizontal
+ Qt::Orientation::Horizontal
@@ -82,7 +82,7 @@
-
- Qt::Horizontal
+ Qt::Orientation::Horizontal
@@ -100,7 +100,7 @@
-
- QFrame::NoFrame
+ QFrame::Shape::NoFrame
@@ -135,7 +135,7 @@
-
- QFrame::NoFrame
+ QFrame::Shape::NoFrame
@@ -150,13 +150,13 @@
-
- QFrame::NoFrame
+ QFrame::Shape::NoFrame
-
- QFrame::NoFrame
+ QFrame::Shape::NoFrame
@@ -189,7 +189,7 @@
-
- Qt::Horizontal
+ Qt::Orientation::Horizontal
@@ -209,7 +209,7 @@
-
- Qt::Horizontal
+ Qt::Orientation::Horizontal
@@ -256,7 +256,7 @@
-
- Qt::Horizontal
+ Qt::Orientation::Horizontal
@@ -276,7 +276,44 @@
-
- Qt::Horizontal
+ Qt::Orientation::Horizontal
+
+
+
+ 40
+ 20
+
+
+
+
+
+
+ -
+
+
-
+
+
+ Qt::Orientation::Horizontal
+
+
+
+ 40
+ 20
+
+
+
+
+ -
+
+
+ Auto align
+
+
+
+ -
+
+
+ Qt::Orientation::Horizontal
@@ -294,7 +331,7 @@
-
- Qt::Vertical
+ Qt::Orientation::Vertical
diff --git a/mapclientplugins/scaffoldcreator/view/scaffoldcreatorwidget.py b/mapclientplugins/scaffoldcreator/view/scaffoldcreatorwidget.py
index 5d52ab8..cf640c9 100644
--- a/mapclientplugins/scaffoldcreator/view/scaffoldcreatorwidget.py
+++ b/mapclientplugins/scaffoldcreator/view/scaffoldcreatorwidget.py
@@ -166,6 +166,7 @@ def _makeConnections(self):
self._scaffold_settings_ui.scale_lineEdit.editingFinished.connect(self._scaleLineEditChanged)
self._scaffold_settings_ui.translation_lineEdit.editingFinished.connect(self._translationLineEditChanged)
self._scaffold_settings_ui.applyTransformation_pushButton.clicked.connect(self._applyTransformationButtonPressed)
+ self._scaffold_settings_ui.autoAlignTransformation_pushButton.clicked.connect(self._autoAlignTransformationButtonPressed)
self._display_settings_ui.displayDataGroup_fieldChooser.setNullObjectName('-')
self._display_settings_ui.displayDataGroup_fieldChooser.setRegion(self._segmentation_data_model.getRegion())
self._display_settings_ui.displayDataGroup_fieldChooser.setConditional(field_is_managed_group)
@@ -700,6 +701,55 @@ def _applyTransformationButtonPressed(self):
self._scaffold_model.applyTransformation(self._display_settings_ui.displayModelCoordinates_fieldChooser.getField())
self._transformationChanged()
+ def _autoAlignTransformationButtonPressed(self):
+ # Create dialog
+ reply = QtWidgets.QDialog(self)
+ reply.setWindowTitle('Confirm action')
+ layout = QtWidgets.QVBoxLayout(reply)
+ hasData = self._segmentation_data_model.hasData()
+ if not hasData:
+ # Add text
+ textLabel = QtWidgets.QLabel('No data file supplied')
+ textLabel.setWordWrap(True)
+ layout.addWidget(textLabel)
+ layout.addSpacing(10)
+ # add Ok Button
+ buttons = QtWidgets.QDialogButtonBox(QtWidgets.QDialogButtonBox.StandardButton.Ok)
+ buttons.accepted.connect(reply.reject)
+ layout.addWidget(buttons)
+ else:
+ # Initilize fitter
+ canAutoAlign = self._scaffold_model.initializeAutoAlignTransformation()
+ if canAutoAlign:
+ # Add text
+ textLabel = QtWidgets.QLabel('Automatically align scaffold to data?')
+ textLabel.setWordWrap(True)
+ layout.addWidget(textLabel)
+ layout.addSpacing(10)
+ # Add buttons
+ buttons = QtWidgets.QDialogButtonBox(
+ QtWidgets.QDialogButtonBox.StandardButton.Yes |
+ QtWidgets.QDialogButtonBox.StandardButton.No
+ )
+ layout.addWidget(buttons)
+ buttons.accepted.connect(reply.accept)
+ buttons.rejected.connect(reply.reject)
+ else:
+ # Add text
+ textLabel = QtWidgets.QLabel('Not enough markers and/or groups' \
+ ' to perform automatic alignment to data')
+ textLabel.setWordWrap(True)
+ layout.addWidget(textLabel)
+ layout.addSpacing(10)
+ # add Ok Button
+ buttons = QtWidgets.QDialogButtonBox(QtWidgets.QDialogButtonBox.StandardButton.Ok)
+ layout.addWidget(buttons)
+ buttons.accepted.connect(reply.reject)
+ # Execute dialog
+ if reply.exec() == QtWidgets.QDialog.Accepted:
+ self._scaffold_model.runAutoAlignTransformation()
+ self._transformationChanged()
+
def _displayDataGroupChanged(self, index):
"""
Callback for change in model coordinates field chooser widget.
diff --git a/mapclientplugins/scaffoldcreator/view/ui_scaffoldsettingswidget.py b/mapclientplugins/scaffoldcreator/view/ui_scaffoldsettingswidget.py
index eb762f0..f1b66e3 100644
--- a/mapclientplugins/scaffoldcreator/view/ui_scaffoldsettingswidget.py
+++ b/mapclientplugins/scaffoldcreator/view/ui_scaffoldsettingswidget.py
@@ -3,7 +3,7 @@
################################################################################
## Form generated from reading UI file 'scaffoldsettingswidget.ui'
##
-## Created by: Qt User Interface Compiler version 6.8.1
+## Created by: Qt User Interface Compiler version 6.9.1
##
## WARNING! All changes made in this file will be lost when recompiling UI file!
################################################################################
@@ -23,7 +23,7 @@ class Ui_ScaffoldSettings(object):
def setupUi(self, ScaffoldSettings):
if not ScaffoldSettings.objectName():
ScaffoldSettings.setObjectName(u"ScaffoldSettings")
- ScaffoldSettings.resize(556, 773)
+ ScaffoldSettings.resize(554, 773)
self.verticalLayout_2 = QVBoxLayout(ScaffoldSettings)
self.verticalLayout_2.setObjectName(u"verticalLayout_2")
self.verticalLayout_2.setContentsMargins(0, 0, 0, 0)
@@ -35,7 +35,7 @@ def setupUi(self, ScaffoldSettings):
sizePolicy.setHeightForWidth(self.subscaffold_frame.sizePolicy().hasHeightForWidth())
self.subscaffold_frame.setSizePolicy(sizePolicy)
self.subscaffold_frame.setMinimumSize(QSize(0, 0))
- self.subscaffold_frame.setFrameShape(QFrame.NoFrame)
+ self.subscaffold_frame.setFrameShape(QFrame.Shape.NoFrame)
self.verticalLayout_5 = QVBoxLayout(self.subscaffold_frame)
self.verticalLayout_5.setObjectName(u"verticalLayout_5")
self.subscaffold_label = QLabel(self.subscaffold_frame)
@@ -71,36 +71,36 @@ def setupUi(self, ScaffoldSettings):
self.meshType_frame = QFrame(ScaffoldSettings)
self.meshType_frame.setObjectName(u"meshType_frame")
- self.meshType_frame.setFrameShape(QFrame.NoFrame)
+ self.meshType_frame.setFrameShape(QFrame.Shape.NoFrame)
self.formLayout = QFormLayout(self.meshType_frame)
self.formLayout.setObjectName(u"formLayout")
self.formLayout.setContentsMargins(0, -1, 0, -1)
self.meshType_label = QLabel(self.meshType_frame)
self.meshType_label.setObjectName(u"meshType_label")
- self.formLayout.setWidget(0, QFormLayout.LabelRole, self.meshType_label)
+ self.formLayout.setWidget(0, QFormLayout.ItemRole.LabelRole, self.meshType_label)
self.meshType_comboBox = QComboBox(self.meshType_frame)
self.meshType_comboBox.setObjectName(u"meshType_comboBox")
- self.formLayout.setWidget(0, QFormLayout.FieldRole, self.meshType_comboBox)
+ self.formLayout.setWidget(0, QFormLayout.ItemRole.FieldRole, self.meshType_comboBox)
self.parameterSet_label = QLabel(self.meshType_frame)
self.parameterSet_label.setObjectName(u"parameterSet_label")
- self.formLayout.setWidget(1, QFormLayout.LabelRole, self.parameterSet_label)
+ self.formLayout.setWidget(1, QFormLayout.ItemRole.LabelRole, self.parameterSet_label)
self.parameterSet_comboBox = QComboBox(self.meshType_frame)
self.parameterSet_comboBox.setObjectName(u"parameterSet_comboBox")
- self.formLayout.setWidget(1, QFormLayout.FieldRole, self.parameterSet_comboBox)
+ self.formLayout.setWidget(1, QFormLayout.ItemRole.FieldRole, self.parameterSet_comboBox)
self.verticalLayout_2.addWidget(self.meshType_frame)
self.meshTypeOptions_frame = QFrame(ScaffoldSettings)
self.meshTypeOptions_frame.setObjectName(u"meshTypeOptions_frame")
- self.meshTypeOptions_frame.setFrameShape(QFrame.NoFrame)
+ self.meshTypeOptions_frame.setFrameShape(QFrame.Shape.NoFrame)
self.verticalLayout_9 = QVBoxLayout(self.meshTypeOptions_frame)
self.verticalLayout_9.setObjectName(u"verticalLayout_9")
self.verticalLayout_9.setContentsMargins(0, -1, 0, -1)
@@ -109,12 +109,12 @@ def setupUi(self, ScaffoldSettings):
self.modifyOptions_frame = QFrame(ScaffoldSettings)
self.modifyOptions_frame.setObjectName(u"modifyOptions_frame")
- self.modifyOptions_frame.setFrameShape(QFrame.NoFrame)
+ self.modifyOptions_frame.setFrameShape(QFrame.Shape.NoFrame)
self.verticalLayout = QVBoxLayout(self.modifyOptions_frame)
self.verticalLayout.setObjectName(u"verticalLayout")
self.deleteElementsRanges_frame = QFrame(self.modifyOptions_frame)
self.deleteElementsRanges_frame.setObjectName(u"deleteElementsRanges_frame")
- self.deleteElementsRanges_frame.setFrameShape(QFrame.NoFrame)
+ self.deleteElementsRanges_frame.setFrameShape(QFrame.Shape.NoFrame)
self.verticalLayout_10 = QVBoxLayout(self.deleteElementsRanges_frame)
self.verticalLayout_10.setObjectName(u"verticalLayout_10")
self.verticalLayout_10.setContentsMargins(0, 0, 0, 0)
@@ -197,6 +197,24 @@ def setupUi(self, ScaffoldSettings):
self.verticalLayout.addLayout(self.horizontalLayout_12)
+ self.horizontalLayout_5 = QHBoxLayout()
+ self.horizontalLayout_5.setObjectName(u"horizontalLayout_5")
+ self.horizontalSpacer_2 = QSpacerItem(40, 20, QSizePolicy.Policy.Expanding, QSizePolicy.Policy.Minimum)
+
+ self.horizontalLayout_5.addItem(self.horizontalSpacer_2)
+
+ self.autoAlignTransformation_pushButton = QPushButton(self.modifyOptions_frame)
+ self.autoAlignTransformation_pushButton.setObjectName(u"autoAlignTransformation_pushButton")
+
+ self.horizontalLayout_5.addWidget(self.autoAlignTransformation_pushButton)
+
+ self.horizontalSpacer = QSpacerItem(40, 20, QSizePolicy.Policy.Expanding, QSizePolicy.Policy.Minimum)
+
+ self.horizontalLayout_5.addItem(self.horizontalSpacer)
+
+
+ self.verticalLayout.addLayout(self.horizontalLayout_5)
+
self.verticalLayout_2.addWidget(self.modifyOptions_frame)
@@ -222,5 +240,6 @@ def retranslateUi(self, ScaffoldSettings):
self.scale_label.setText(QCoreApplication.translate("ScaffoldSettings", u"Scale x, y, z:", None))
self.translation_label.setText(QCoreApplication.translate("ScaffoldSettings", u"Translation x, y, z", None))
self.applyTransformation_pushButton.setText(QCoreApplication.translate("ScaffoldSettings", u"Apply transformation", None))
+ self.autoAlignTransformation_pushButton.setText(QCoreApplication.translate("ScaffoldSettings", u"Auto align", None))
# retranslateUi