From 297dec065ab08eb863366d765abfd4dd1df8d46b Mon Sep 17 00:00:00 2001 From: Aleks Berland Date: Tue, 9 Sep 2025 11:03:46 -0400 Subject: [PATCH] Add select_instances_in_host method to PublisherController and CreateModel Implemented select_instances_in_host in PublisherController to facilitate instance selection in the host. Enhanced CreateModel with the corresponding method to handle instance selection and focus in DCC, including error handling for selection hooks. Updated OverviewWidget to connect double-click events to the new instance selection functionality while preserving existing behavior. --- client/ayon_core/tools/publisher/control.py | 4 +++ .../tools/publisher/models/create.py | 30 +++++++++++++++++++ .../publisher/widgets/overview_widget.py | 19 ++++++++++-- 3 files changed, 50 insertions(+), 3 deletions(-) diff --git a/client/ayon_core/tools/publisher/control.py b/client/ayon_core/tools/publisher/control.py index 038816c6fc..cef44bd6ee 100644 --- a/client/ayon_core/tools/publisher/control.py +++ b/client/ayon_core/tools/publisher/control.py @@ -526,6 +526,10 @@ class PublisherController( """ self._create_model.remove_instances(instance_ids) + def select_instances_in_host(self, instance_ids): + """Ask host/creators to select and focus selected instances.""" + return self._create_model.select_instances_in_host(list(instance_ids)) + def publish_has_started(self): return self._publish_model.has_started() diff --git a/client/ayon_core/tools/publisher/models/create.py b/client/ayon_core/tools/publisher/models/create.py index 5098826b8b..56c7c3eb3f 100644 --- a/client/ayon_core/tools/publisher/models/create.py +++ b/client/ayon_core/tools/publisher/models/create.py @@ -785,6 +785,36 @@ class CreateModel: # is not required. self._remove_instances_from_context(instance_ids) + def select_instances_in_host(self, instance_ids: List[str]): + """Ask host/creator to select and focus instances in DCC. + + Calls creator-specific hook 'select_in_host' when available. + + Args: + instance_ids (List[str]): Instance identifiers to select. + """ + if not instance_ids: + return + for instance_id in instance_ids: + instance = self._get_instance_by_id(instance_id) + if instance is None: + continue + try: + creator_identifier = instance.creator_identifier + creator = self._creators.get(creator_identifier) + if creator is None: + continue + # Call optional hook if present on the creator + select_hook = getattr(creator, "select_in_host", None) + if callable(select_hook): + select_hook(instance) + except Exception as e: + # Never raise from a UX helper + self.log.debug( + "Selection hook failed for instance %s", instance_id, exc_info=True + ) + self.log.error(f"Selection hook failed for instance {instance_id}: {e}") + def set_instances_create_attr_values(self, instance_ids, key, value): self._set_instances_create_attr_values(instance_ids, key, value) diff --git a/client/ayon_core/tools/publisher/widgets/overview_widget.py b/client/ayon_core/tools/publisher/widgets/overview_widget.py index 01799ac908..bd66a51d89 100644 --- a/client/ayon_core/tools/publisher/widgets/overview_widget.py +++ b/client/ayon_core/tools/publisher/widgets/overview_widget.py @@ -127,19 +127,19 @@ class OverviewWidget(QtWidgets.QFrame): self._on_product_change ) product_list_view.double_clicked.connect( - self.publish_tab_requested + self._on_instances_double_clicked ) product_list_view_grouped.selection_changed.connect( self._on_product_change ) product_list_view_grouped.double_clicked.connect( - self.publish_tab_requested + self._on_instances_double_clicked ) product_view_cards.selection_changed.connect( self._on_product_change ) product_view_cards.double_clicked.connect( - self.publish_tab_requested + self._on_instances_double_clicked ) # Instance context has changed product_attributes_widget.convert_requested.connect( @@ -544,3 +544,16 @@ class OverviewWidget(QtWidgets.QFrame): def _on_instances_removed(self): self._refresh_instances() + + def _on_instances_double_clicked(self): + # On double-click, select and focus corresponding nodes in host + instance_ids, _, _ = self.get_selected_items() + if not instance_ids: + return + try: + self._controller.select_instances_in_host(instance_ids) + except Exception: + # Keep UI responsive even if host-side selection fails + pass + # Keep existing behavior: navigate to publish tab + self.publish_tab_requested.emit()