diff --git a/src/napari_clusters_plotter/_algorithm_widget.py b/src/napari_clusters_plotter/_algorithm_widget.py index b9c2f9c5..cfde141c 100644 --- a/src/napari_clusters_plotter/_algorithm_widget.py +++ b/src/napari_clusters_plotter/_algorithm_widget.py @@ -39,7 +39,7 @@ def _get_features(self): _features = layer.features[self.common_columns].copy() # Add layer name as a categorical column - _features["layer"] = layer.unique_id + _features["layer"] = layer.name _features["layer"] = _features["layer"].astype("category") features = pd.concat([features, _features], axis=0) diff --git a/src/napari_clusters_plotter/_dim_reduction_and_clustering.py b/src/napari_clusters_plotter/_dim_reduction_and_clustering.py index 61570e41..483e28e4 100644 --- a/src/napari_clusters_plotter/_dim_reduction_and_clustering.py +++ b/src/napari_clusters_plotter/_dim_reduction_and_clustering.py @@ -62,7 +62,7 @@ def _process_result(self, result): # add the columns to the features layer_feature_subset = features_clustered[ - features_clustered["layer"] == layer.unique_id + features_clustered["layer"] == layer.name ] current_features[column_name] = layer_feature_subset[ column_name @@ -114,7 +114,7 @@ def _process_result(self, result: pd.DataFrame): current_features = layer.features for column in column_names: layer_feature_subset = result[ - result["layer"] == layer.unique_id + result["layer"] == layer.name ] # add the columns to the features diff --git a/src/napari_clusters_plotter/_new_plotter_widget.py b/src/napari_clusters_plotter/_new_plotter_widget.py index 0d4bf7a2..d4936349 100644 --- a/src/napari_clusters_plotter/_new_plotter_widget.py +++ b/src/napari_clusters_plotter/_new_plotter_widget.py @@ -145,7 +145,7 @@ def _on_export_clusters(self): # get the layer to export from for layer in self.layers: features_subset = features[ - features["layer"] == layer.unique_id + features["layer"] == layer.name ].reset_index() indices = features_subset[hue_column].values == selected_cluster if not np.any(indices): @@ -243,7 +243,7 @@ def _on_finish_draw(self, color_indices: np.ndarray): features = self._get_features() for layer in self.layers: layer_indices = features[ - features["layer"] == layer.unique_id + features["layer"] == layer.name ].index # store latest cluster indeces in the features table @@ -727,7 +727,7 @@ def _update_layer_colors(self, use_color_indices: bool = False) -> None: active_artist.color_indices ) layer_indices = features[ - features["layer"] == selected_layer.unique_id + features["layer"] == selected_layer.name ].index self._set_layer_color( selected_layer, rgba_colors[layer_indices] @@ -810,15 +810,12 @@ def _on_highlighted_changed(self, boolean_object_selected: bool): if not np.any(boolean_object_selected): return if np.count_nonzero(boolean_object_selected) > 1: - print( - "Focus only works for single object selection, not focusing." + napari.utils.notifications.show_info( + "Multiple objects selected - only single objects can be highlighted." ) return features = self._get_features() - features_sub = features.iloc[ - np.argwhere(boolean_object_selected).flatten() - ] - layer = features_sub["layer"].values[0] + layer = features[boolean_object_selected]["layer"].values[0] boolean_object_selected_in_layer = boolean_object_selected[ features["layer"] == layer ] @@ -882,7 +879,7 @@ def _focus_object(layer, boolean_object_selected): transformed_center = _apply_affine_transform( center, n_dims, affine_net ) - _set_viewer_camera(viewer, transformed_center) + # Set the selected data in the layer (only displays if single layer is selected) layer.selected_data = set( np.argwhere(boolean_object_selected).flatten() @@ -895,7 +892,6 @@ def _focus_object(layer, boolean_object_selected): transformed_center = _apply_affine_transform( center, n_dims, affine_net ) - _set_viewer_camera(viewer, transformed_center) # Set the selected data in the layer (only displays if single layer is selected) layer.selected_label = selected_label elif isinstance(layer, napari.layers.Surface): @@ -904,7 +900,6 @@ def _focus_object(layer, boolean_object_selected): transformed_center = _apply_affine_transform( center, n_dims, affine_net ) - _set_viewer_camera(viewer, transformed_center) elif isinstance(layer, napari.layers.Shapes): selected_shape = layer.data[ np.nonzero(boolean_object_selected)[0][0] @@ -914,7 +909,6 @@ def _focus_object(layer, boolean_object_selected): transformed_center = _apply_affine_transform( center, n_dims, affine_net ) - _set_viewer_camera(viewer, transformed_center) layer.selected_data = set( np.argwhere(boolean_object_selected).flatten() ) @@ -925,7 +919,8 @@ def _focus_object(layer, boolean_object_selected): transformed_center = _apply_affine_transform( center, n_dims, affine_net ) - _set_viewer_camera(viewer, transformed_center) + + _set_viewer_camera(viewer, transformed_center) # TODO: Optionally uncomment this and call it in _set_viewer_camera if we want to zoom-in on highlighted objects diff --git a/src/napari_clusters_plotter/_tests/test_dimensionality_reduction.py b/src/napari_clusters_plotter/_tests/test_dimensionality_reduction.py index 2ef06358..096af358 100644 --- a/src/napari_clusters_plotter/_tests/test_dimensionality_reduction.py +++ b/src/napari_clusters_plotter/_tests/test_dimensionality_reduction.py @@ -128,7 +128,7 @@ def test_layer_update(make_napari_viewer, widget_config): for layer in possible_selection: for feature in widget.common_columns: assert feature in collected_features.columns - assert layer.unique_id in collected_features["layer"].values + assert layer.name in collected_features["layer"].values def test_feature_update(make_napari_viewer, widget_config): diff --git a/src/napari_clusters_plotter/_tests/test_plotter.py b/src/napari_clusters_plotter/_tests/test_plotter.py index 8cddef8c..cc7ed720 100644 --- a/src/napari_clusters_plotter/_tests/test_plotter.py +++ b/src/napari_clusters_plotter/_tests/test_plotter.py @@ -801,16 +801,27 @@ def test_focus_object_on_highlighted_multi_selected_points_layers( boolean_object_selected = np.zeros( len(layer.data) + len(layer2.data), dtype=bool ) - boolean_object_selected[len(layer.data) + 3] = True + boolean_object_selected[np.random.randint(0, len(boolean_object_selected))] = True + layer_name = widget._get_features()[boolean_object_selected]['layer'].values[0] + layer = viewer.layers[layer_name] # Set highlighted property widget.plotting_widget.active_artist.highlighted = boolean_object_selected # Check that the viewer camera is centered on the selected point (considering layer translation) - np.testing.assert_allclose( - viewer.camera.center, layer2.data[3][-3:] + translate, rtol=1e-5 + index_in_data = np.where( + boolean_object_selected[widget._get_features()['layer'] == layer_name] + )[0][0] + assert np.allclose( + np.asarray(viewer.camera.center), layer.data[index_in_data][-3:] + layer.translate[-3:], rtol=1e-5 ) # Check that the viewer's current step is set to the selected point - np.testing.assert_allclose( - viewer.dims.current_step[0], layer2.data[3][0], rtol=1e-5 + assert np.allclose( + viewer.dims.current_step[0], layer.data[index_in_data][0], rtol=1e-5 ) + + +if __name__ == '__main__': + import napari + + test_focus_object_on_highlighted_multi_selected_points_layers(napari.Viewer) \ No newline at end of file