From abfb0aedee18debe9b4ec9f6e1053cdde7e1a7d9 Mon Sep 17 00:00:00 2001 From: Jakub Trllo <43494761+iLLiCiTiT@users.noreply.github.com> Date: Mon, 7 Apr 2025 16:18:49 +0200 Subject: [PATCH] changed how thumbnails are received --- client/ayon_core/pipeline/thumbnails.py | 19 +++++- .../tools/common_models/thumbnails.py | 61 +++++++++++++++++-- client/ayon_core/tools/loader/abstract.py | 12 +++- client/ayon_core/tools/loader/control.py | 11 +++- client/ayon_core/tools/loader/ui/window.py | 45 ++++++-------- 5 files changed, 109 insertions(+), 39 deletions(-) diff --git a/client/ayon_core/pipeline/thumbnails.py b/client/ayon_core/pipeline/thumbnails.py index 401d95f273..658372888f 100644 --- a/client/ayon_core/pipeline/thumbnails.py +++ b/client/ayon_core/pipeline/thumbnails.py @@ -226,11 +226,26 @@ class _CacheItems: thumbnails_cache = ThumbnailsCache() -def get_thumbnail_path(project_name, thumbnail_id): +def get_thumbnail_path( + project_name: str, + entity_type: str, + entity_id: str, + thumbnail_id: str +): """Get path to thumbnail image. + Thumbnail is cached by thumbnail id but is received using entity type and + entity id. + + Notes: + Function 'get_thumbnail_by_id' can't be used because does not work + for artists. The endpoint can't validate artist permissions. + Args: project_name (str): Project where thumbnail belongs to. + entity_type (str): Entity type "folder", "task", "version" + and "workfile". + entity_id (str): Entity id. thumbnail_id (Union[str, None]): Thumbnail id. Returns: @@ -251,7 +266,7 @@ def get_thumbnail_path(project_name, thumbnail_id): # 'get_thumbnail_by_id' did not return output of # 'ServerAPI' method. con = ayon_api.get_server_api_connection() - result = con.get_thumbnail_by_id(project_name, thumbnail_id) + result = con.get_thumbnail(project_name, entity_type, entity_id) if result is not None and result.is_valid: return _CacheItems.thumbnails_cache.store_thumbnail( diff --git a/client/ayon_core/tools/common_models/thumbnails.py b/client/ayon_core/tools/common_models/thumbnails.py index 2fa1e36e5c..5111d0be28 100644 --- a/client/ayon_core/tools/common_models/thumbnails.py +++ b/client/ayon_core/tools/common_models/thumbnails.py @@ -21,8 +21,50 @@ class ThumbnailsModel: self._folders_cache.reset() self._versions_cache.reset() - def get_thumbnail_path(self, project_name, thumbnail_id): - return self._get_thumbnail_path(project_name, thumbnail_id) + def get_thumbnail_paths( + self, + project_name, + entity_type, + entity_ids, + ): + thumbnail_paths = set() + if not project_name or not entity_type or not entity_ids: + return thumbnail_paths + + thumbnail_id_by_entity_id = {} + if entity_type == "folder": + thumbnail_id_by_entity_id = self.get_folder_thumbnail_ids( + project_name, entity_ids + ) + + elif entity_type == "version": + thumbnail_id_by_entity_id = self.get_version_thumbnail_ids( + project_name, entity_ids + ) + + if not thumbnail_id_by_entity_id: + return thumbnail_paths + + entity_ids_by_thumbnail_id = collections.defaultdict(set) + for entity_id, thumbnail_id in thumbnail_id_by_entity_id.items(): + if not thumbnail_id: + continue + entity_ids_by_thumbnail_id[thumbnail_id].add(entity_id) + + output = { + entity_id: None + for entity_id in entity_ids + } + for thumbnail_id, entity_ids in entity_ids_by_thumbnail_id.items(): + thumbnail_path = self._get_thumbnail_path( + project_name, entity_type, next(iter(entity_ids)), thumbnail_id + ) + if not thumbnail_path: + continue + for entity_id in entity_ids: + output[entity_id] = thumbnail_path + + return output def get_folder_thumbnail_ids(self, project_name, folder_ids): project_cache = self._folders_cache[project_name] @@ -56,7 +98,13 @@ class ThumbnailsModel: output[version_id] = cache.get_data() return output - def _get_thumbnail_path(self, project_name, thumbnail_id): + def _get_thumbnail_path( + self, + project_name, + entity_type, + entity_id, + thumbnail_id + ): if not thumbnail_id: return None @@ -64,7 +112,12 @@ class ThumbnailsModel: if thumbnail_id in project_cache: return project_cache[thumbnail_id] - filepath = get_thumbnail_path(project_name, thumbnail_id) + filepath = get_thumbnail_path( + project_name, + entity_type, + entity_id, + thumbnail_id + ) project_cache[thumbnail_id] = filepath return filepath diff --git a/client/ayon_core/tools/loader/abstract.py b/client/ayon_core/tools/loader/abstract.py index 26b476de1f..d0d7cd430b 100644 --- a/client/ayon_core/tools/loader/abstract.py +++ b/client/ayon_core/tools/loader/abstract.py @@ -733,7 +733,12 @@ class FrontendLoaderController(_BaseLoaderController): pass @abstractmethod - def get_thumbnail_path(self, project_name, thumbnail_id): + def get_thumbnail_paths( + self, + project_name, + entity_type, + entity_ids + ): """Get thumbnail path for thumbnail id. This method should get a path to a thumbnail based on thumbnail id. @@ -742,10 +747,11 @@ class FrontendLoaderController(_BaseLoaderController): Args: project_name (str): Project name. - thumbnail_id (str): Thumbnail id. + entity_type (str): Entity type. + entity_ids (set[str]): Entity ids. Returns: - Union[str, None]: Thumbnail path or None if not found. + dict[str, Union[str, None]]: Thumbnail path by entity id. """ pass diff --git a/client/ayon_core/tools/loader/control.py b/client/ayon_core/tools/loader/control.py index 7959a63edb..b3a80b34d4 100644 --- a/client/ayon_core/tools/loader/control.py +++ b/client/ayon_core/tools/loader/control.py @@ -259,9 +259,14 @@ class LoaderController(BackendLoaderController, FrontendLoaderController): project_name, version_ids ) - def get_thumbnail_path(self, project_name, thumbnail_id): - return self._thumbnails_model.get_thumbnail_path( - project_name, thumbnail_id + def get_thumbnail_paths( + self, + project_name, + entity_type, + entity_ids, + ): + return self._thumbnails_model.get_thumbnail_paths( + project_name, entity_type, entity_ids ) def change_products_group(self, project_name, product_ids, group_name): diff --git a/client/ayon_core/tools/loader/ui/window.py b/client/ayon_core/tools/loader/ui/window.py index b846484c39..3d2e15c630 100644 --- a/client/ayon_core/tools/loader/ui/window.py +++ b/client/ayon_core/tools/loader/ui/window.py @@ -501,38 +501,29 @@ class LoaderWindow(QtWidgets.QWidget): self._update_thumbnails() def _update_thumbnails(self): + # TODO make this threaded and show loading animation while running project_name = self._selected_project_name - thumbnail_ids = set() + entity_type = None + entity_ids = set() if self._selected_version_ids: - thumbnail_id_by_entity_id = ( - self._controller.get_version_thumbnail_ids( - project_name, - self._selected_version_ids - ) - ) - thumbnail_ids = set(thumbnail_id_by_entity_id.values()) + entity_ids = set(self._selected_version_ids) + entity_type = "version" elif self._selected_folder_ids: - thumbnail_id_by_entity_id = ( - self._controller.get_folder_thumbnail_ids( - project_name, - self._selected_folder_ids - ) - ) - thumbnail_ids = set(thumbnail_id_by_entity_id.values()) + entity_ids = set(self._selected_folder_ids) + entity_type = "folder" - thumbnail_ids.discard(None) - - if not thumbnail_ids: - self._thumbnails_widget.set_current_thumbnails(None) - return - - thumbnail_paths = set() - for thumbnail_id in thumbnail_ids: - thumbnail_path = self._controller.get_thumbnail_path( - project_name, thumbnail_id) - thumbnail_paths.add(thumbnail_path) + thumbnail_path_by_entity_id = self._controller.get_thumbnail_paths( + project_name, entity_type, entity_ids + ) + thumbnail_paths = set(thumbnail_path_by_entity_id.values()) thumbnail_paths.discard(None) - self._thumbnails_widget.set_current_thumbnail_paths(thumbnail_paths) + + if thumbnail_paths: + self._thumbnails_widget.set_current_thumbnail_paths( + thumbnail_paths + ) + else: + self._thumbnails_widget.set_current_thumbnails(None) def _on_projects_refresh(self): self._refresh_handler.set_project_refreshed()