Exemple #1
0
class TomographyPlugin(GUIPlugin):
    name = "Tomography"

    def __init__(self, *args, **kwargs):
        self.active_filename = ""

        self._main_view = QMainWindow()
        self._main_view.setCentralWidget(QWidget())
        self._main_view.centralWidget().hide()

        self._editors = QStackedWidget()

        self.workflow_process_selector = QComboBox()
        self.workflow_process_selector.setSizePolicy(QSizePolicy.Preferred, QSizePolicy.Fixed)

        self.workflow_process_selector.addItem("TomoPy Workflow")

        self._workflow = None

        self._tomo_workflow = TomographyWorkflow()  # Create a workflow
        self._workflow = self._tomo_workflow

        self._workflow_editor = WorkflowEditor(workflow=self._workflow)
        self._workflow_editor.sigRunWorkflow.connect(self.run_workflow)

        self._active_workflow_executor = QTreeWidget()

        self._editors.addWidget(self._workflow_editor)

        if hasLTT:
            self._alt_workflow = LTTWorkflow()
            self.workflow_process_selector.addItem("LTT Workflow")
            self._alt_workflow_editor = WorkflowEditor(self._alt_workflow)
            self._alt_workflow_editor.sigRunWorkflow.connect(self.run_workflow)
            self._editors.addWidget(self._alt_workflow_editor)

        self.workflow_process_selector.setCurrentIndex(0)
        self.workflow_process_selector.currentIndexChanged.connect(self.active_workflow_changed)

        self._active_workflow_widget = QWidget()
        self._active_layout = QVBoxLayout()

        self._active_layout.addWidget(self.workflow_process_selector)
        self._active_layout.addWidget(self._editors)
        self._active_layout.addWidget(self._active_workflow_executor)

        self._active_workflow_widget.setLayout(self._active_layout)

        # self.hdf5_viewer = HDFTreeViewer()
        # self.hdf5_viewer.load("/Users/hari/20200521_160002_heartbeat_test.h5")

        self.top_controls = QWidget()
        self.top_controls_layout = QHBoxLayout()
        self.top_controls.setLayout(self.top_controls_layout)
        self.top_controls_add_new_selector = QComboBox()
        self.top_controls_frequency_selector = QSpinBox()
        self.top_controls_frequency_selector.setValue(0)

        self.top_controls_add_new_viewer = QPushButton()
        self.top_controls_add_new_viewer.setText("Add Viewer")
        self.top_controls_add_new_viewer.clicked.connect(self.add_new_viewer_selected)

        self.top_controls_preview = QPushButton()
        self.top_controls_preview.setText("Preview")
        self.top_controls_preview.clicked.connect(self.preview_workflows)

        self.top_controls_execute = QPushButton()
        self.top_controls_execute.setText("Execute All")
        self.top_controls_execute.clicked.connect(self.execute_workflows)

        self.top_controls_add_new_selector.setSizePolicy(QSizePolicy.Preferred, QSizePolicy.Preferred)
        self.top_controls_add_new_viewer.setSizePolicy(QSizePolicy.Fixed, QSizePolicy.Fixed)
        self.top_controls_execute.setSizePolicy(QSizePolicy.Fixed, QSizePolicy.Fixed)
        self.top_controls_frequency_selector.setSizePolicy(QSizePolicy.Fixed, QSizePolicy.Fixed)

        self.top_controls_layout.addWidget(self.top_controls_add_new_selector)
        self.top_controls_layout.addWidget(self.top_controls_add_new_viewer)
        self.top_controls_layout.addWidget(self.top_controls_frequency_selector)
        self.top_controls_layout.addWidget(self.top_controls_preview)
        self.top_controls_layout.addWidget(self.top_controls_execute)

        self.top_controls.setLayout(self.top_controls_layout)

        self.status_bar = QLabel("None Loaded...")

        # Create a layout to organize our widgets
        # The first argument (which corresponds to the center widget) is required.
        catalog_viewer_layout = GUILayout(self._main_view,
                                          top=self.top_controls,
                                          right=self._active_workflow_widget,
                                          bottom=self.status_bar)

        # Create a "View" stage that has the catalog viewer layout
        self.stages = {"View": catalog_viewer_layout}

        self.active_workflows = []

        # For classes derived from GUIPlugin, this super __init__ must occur at end
        super(TomographyPlugin, self).__init__(*args, **kwargs)

    def active_workflow_changed(self, index):
        self._editors.setCurrentIndex(index)

        if index == 0:
            self._workflow = self._tomo_workflow
        else:
            self._workflow = self._alt_workflow

    def preview_workflows(self):
        if len(self.active_filename) == 0:
            return

        preview_sinogram = self.top_controls_frequency_selector.value()

        workflows = []
        for aw in range(self._active_workflow_executor.topLevelItemCount()):
            widget_item = self._active_workflow_executor.topLevelItem(aw)
            workflow = widget_item.data(0, Qt.UserRole)
            workflows.append(workflow)

        active_workflows = self.active_workflows

        for workflow in workflows:
            def results_ready(workflow, *results):
                output_image = results[0]["recon"]  # We want the output_image from the last operation
                # print("RECON SHAPE", output_image.shape)
                for active_workflow in active_workflows:
                    if active_workflow[1] == workflow:
                        active_workflow[0].widget().setImage(output_image)  # Update the result view widget
            workflow.execute(callback_slot=partial(results_ready, workflow), path=self.active_filename, sinoindex=preview_sinogram)

    def execute_workflows(self):
        if len(self.active_filename) == 0:
            return

        workflows = []
        for aw in range(self._active_workflow_executor.topLevelItemCount()):
            widget_item = self._active_workflow_executor.topLevelItem(aw)
            workflow = widget_item.data(0, Qt.UserRole)
            workflows.append(workflow)

        active_workflows = self.active_workflows

        for workflow in workflows:
            def results_ready(workflow, *results):
                output_image = results[0]["recon"]  # We want the output_image from the last operation
                # print("RECON SHAPE", output_image.shape)
                for active_workflow in active_workflows:
                    if active_workflow[1] == workflow:
                        active_workflow[0].widget().setImage(output_image)  # Update the result view widget
            workflow.execute(callback_slot=partial(results_ready, workflow), path=self.active_filename)

    def add_new_viewer_selected(self, checked):
        if self.top_controls_add_new_selector.count() == 0:
            return

        selected = self.top_controls_add_new_selector.currentIndex()

        if selected < 0:
            return

        workflow = self.top_controls_add_new_selector.currentData(Qt.UserRole)
        print("WORKFLOW", workflow, workflow.name)

        dock_widget = QDockWidget()
        viewer = CatalogView()
        dock_widget.setWidget(viewer)
        dock_widget.setWindowTitle(workflow.name)

        if len(self.active_workflows) == 0:
            self._main_view.addDockWidget(Qt.RightDockWidgetArea, dock_widget)
        else:
            self._main_view.tabifyDockWidget(self.active_workflows[-1][0], dock_widget)

        self.active_workflows.append((dock_widget, workflow))

    def appendHeader(self, header, **kwargs):
        filename = header._documents["start"][0]["filename"]
        self.active_filename = filename

        self.status_bar.setText("Loading Filename:" + filename)
        
        dataset, bkgs, drks = read_als_hdf5(filename)
        slice_widget = MyCatalogView()
        dw = QDockWidget()
        dw.setWidget(slice_widget)
        dw.setWindowTitle(filename)
        slice_widget.setImage(dataset)

        dock_children = self._main_view.findChildren(QDockWidget)
        print(dock_children)

        #if len(dock_children) == 0:
        #    self._main_view.addDockWidget(Qt.LeftDockWidgetArea, dw)
        #else:
        #    self._main_view.tabifyDockWidget(dock_children[0], dw)

        self._main_view.addDockWidget(Qt.LeftDockWidgetArea, dw)
        self.status_bar.setText("Done Loading Filename:" + filename)

    def appendCatalog(self, catalog, **kwargs):
        """Re-implemented from GUIPlugin - gives us access to a catalog reference
        You MUST implement this method if you want to load catalog data into your GUIPlugin.
        """
        # Set the catalog viewer's catalog, stream, and field (so it knows what to display)
        # This is a quick and simple demonstration; stream and field should NOT be hardcoded
        # stream = "primary"
        # field = "img"
        # self._catalog_viewer.setCatalog(catalog, stream, field)
        print("CATALOG CALLED", catalog)
        pass

    def run_workflow(self):
        """Run the internal workflowi.
        In this example, this will be called whenever the "Run Workflow" in the WorkflowEditor is clicked.
        """
        item = QTreeWidgetItem()

        workflow_name = self._workflow.name + ":" + str(self._active_workflow_executor.model().rowCount())
        workflow = self._workflow.clone()
        workflow.name = workflow_name
        workflow._pretty_print()

        item.setText(0, workflow_name)
        item.setData(0, Qt.UserRole, workflow)
        self._active_workflow_executor.addTopLevelItem(item)
        self.top_controls_add_new_selector.addItem(workflow_name, userData=workflow)