[Bf-extensions-cvs] [692a15f3] master: BlenderKit: fixes and optimizations

Vilem Duha noreply at git.blender.org
Tue Jul 20 14:27:17 CEST 2021


Commit: 692a15f3c50c57cc3b66115aa5f316aa290ddc0a
Author: Vilem Duha
Date:   Tue Jul 20 14:26:26 2021 +0200
Branches: master
https://developer.blender.org/rBA692a15f3c50c57cc3b66115aa5f316aa290ddc0a

BlenderKit: fixes and optimizations

Search results aren't passed around back to search and are parsed only once. Same for previews.
Search function could run many times per second when more pages were loaded.
Search now causes almost no lag in Blender thanks to the fixes
Default page size in search request is now fit to the asset bar size settings.
several optimizations in the draw code - is now about 3x faster
rerequests now can return a fake response in case of a timeout

===================================================================

M	blenderkit/__init__.py
M	blenderkit/asset_bar_op.py
M	blenderkit/ratings.py
M	blenderkit/ratings_utils.py
M	blenderkit/rerequests.py
M	blenderkit/search.py
M	blenderkit/ui.py
M	blenderkit/ui_panels.py
M	blenderkit/upload.py

===================================================================

diff --git a/blenderkit/__init__.py b/blenderkit/__init__.py
index 7fc744a0..7b22279d 100644
--- a/blenderkit/__init__.py
+++ b/blenderkit/__init__.py
@@ -19,7 +19,7 @@
 bl_info = {
     "name": "BlenderKit Online Asset Library",
     "author": "Vilem Duha, Petr Dlouhy",
-    "version": (2, 93, 0),
+    "version": (3, 0, 0),
     "blender": (2, 93, 0),
     "location": "View3D > Properties > BlenderKit",
     "description": "Online BlenderKit library (materials, models, brushes and more). Connects to the internet.",
@@ -141,8 +141,6 @@ from bpy.types import (
 
 @persistent
 def scene_load(context):
-    if not bpy.app.background:
-        search.load_previews()
     ui_props = bpy.context.scene.blenderkitUI
     ui_props.assetbar_on = False
     ui_props.turn_off = False
diff --git a/blenderkit/asset_bar_op.py b/blenderkit/asset_bar_op.py
index 0ad63a83..9c12b0f2 100644
--- a/blenderkit/asset_bar_op.py
+++ b/blenderkit/asset_bar_op.py
@@ -559,8 +559,15 @@ class BlenderKitAssetBarOperator(BL_UI_OT_draw_operator):
 
     def search_more(self):
         sro = bpy.context.window_manager.get('search results orig')
-        if sro is not None and sro.get('next') is not None:
-            blenderkit.search.search(get_next=True)
+        if sro is None:
+            return;
+        if sro.get('next') is None:
+            return
+        search_props = utils.get_search_props()
+        if search_props.is_searching:
+            return
+
+        blenderkit.search.search(get_next=True)
 
     def update_images(self):
         sr = bpy.context.window_manager.get('search results')
diff --git a/blenderkit/ratings.py b/blenderkit/ratings.py
index 8c4c2b63..4bfcfd53 100644
--- a/blenderkit/ratings.py
+++ b/blenderkit/ratings.py
@@ -268,7 +268,7 @@ def rating_menu_draw(self, context):
     layout = self.layout
 
     ui_props = context.scene.blenderkitUI
-    sr = bpy.context.window_manager['search results orig']
+    sr = bpy.context.window_manager['search results']
 
     asset_search_index = ui_props.active_index
     if asset_search_index > -1:
diff --git a/blenderkit/ratings_utils.py b/blenderkit/ratings_utils.py
index 9a282944..37c1c971 100644
--- a/blenderkit/ratings_utils.py
+++ b/blenderkit/ratings_utils.py
@@ -76,9 +76,9 @@ def store_rating_local_empty(asset_id):
 
 def store_rating_local(asset_id, type='quality', value=0):
     context = bpy.context
-    context.window_manager['asset ratings'] = context.window_manager.get('asset ratings', {})
-    context.window_manager['asset ratings'][asset_id] = context.window_manager['asset ratings'].get(asset_id, {})
-    context.window_manager['asset ratings'][asset_id][type] = value
+    ar   = context.window_manager['asset ratings']
+    ar[asset_id] = ar.get(asset_id, {})
+    ar[asset_id][type] = value
 
 
 def get_rating(asset_id, headers):
@@ -96,6 +96,8 @@ def get_rating(asset_id, headers):
     url = paths.get_api_url() + 'assets/' + asset_id + '/rating/'
     params = {}
     r = rerequests.get(url, params=params, verify=True, headers=headers)
+    if r is None:
+        return
     if r.status_code == 200:
         rj = r.json()
         ratings = {}
diff --git a/blenderkit/rerequests.py b/blenderkit/rerequests.py
index f9c51559..735feb35 100644
--- a/blenderkit/rerequests.py
+++ b/blenderkit/rerequests.py
@@ -26,6 +26,13 @@ import logging
 bk_logger = logging.getLogger('rerequests')
 
 
+class FakeResponse():
+    def __init__(self, text='', status_code = 400):
+        self.text = text
+        self.status_code = status_code
+    def json(self):
+        return {}
+
 def rerequest(method, url, recursion=0, **kwargs):
     # first get any additional args from kwargs
     immediate = False
@@ -37,7 +44,9 @@ def rerequest(method, url, recursion=0, **kwargs):
         response = requests.request(method, url, **kwargs)
     except Exception as e:
         print(e)
-        return None
+        tasks_queue.add_task((ui.add_report, (
+            'Connection error.', 10)))
+        return FakeResponse()
 
     bk_logger.debug(url + str(kwargs))
     bk_logger.debug(response.status_code)
diff --git a/blenderkit/search.py b/blenderkit/search.py
index c4796f4c..d8344aca 100644
--- a/blenderkit/search.py
+++ b/blenderkit/search.py
@@ -52,6 +52,7 @@ import urllib
 import queue
 import logging
 
+
 bk_logger = logging.getLogger('blenderkit')
 
 search_start_time = 0
@@ -70,6 +71,8 @@ def check_errors(rdata):
             return False, 'Use login panel to connect your profile.'
         else:
             return False, rdata.get('detail')
+    if rdata.get('statusCode') is None and rdata.get('results') is None:
+        return False, 'Connection error'
     return True, ''
 
 
@@ -287,19 +290,8 @@ def parse_result(r):
         # so blender's data is same as on server.
         asset_data = {'thumbnail': tname,
                       'thumbnail_small': small_tname,
-                      # 'thumbnails':allthumbs,
-                      # 'download_url': durl, #made obsolete since files are stored in orig form.
-                      # 'id': r['id'],
-                      # 'asset_base_id': r['assetBaseId'],#this should stay ONLY for compatibility with older scenes
-                      # 'name': r['name'],
-                      # 'asset_type': r['assetType'], #this should stay ONLY for compatibility with older scenes
                       'tooltip': tooltip,
-                      # 'tags': r['tags'],
-                      # 'can_download': r.get('canDownload', True),#this should stay ONLY for compatibility with older scenes
-                      # 'verification_status': r['verificationStatus'],#this should stay ONLY for compatibility with older scenes
-                      # 'author_id': r['author']['id'],#this should stay ONLY for compatibility with older scenes
-                      # 'author': r['author']['firstName'] + ' ' + r['author']['lastName']
-                      # 'description': r['description'],
+
                       }
         asset_data['downloaded'] = 0
 
@@ -351,6 +343,7 @@ def parse_result(r):
 
 # @bpy.app.handlers.persistent
 def search_timer():
+
     # this makes a first search after opening blender. showing latest assets.
     # utils.p('timer search')
     # utils.p('start search timer')
@@ -381,7 +374,8 @@ def search_timer():
     global search_threads
     if len(search_threads) == 0:
         # utils.p('end search timer')
-
+        props = utils.get_search_props()
+        props.is_searching = False
         return 1.0
     # don't do anything while dragging - this could switch asset during drag, and make results list length different,
     # causing a lot of throuble.
@@ -389,34 +383,29 @@ def search_timer():
         # utils.p('end search timer')
 
         return 0.5
+
     for thread in search_threads:
         # TODO this doesn't check all processes when one gets removed,
         # but most of the time only one is running anyway
         if not thread[0].is_alive():
+
             search_threads.remove(thread)  #
             icons_dir = thread[1]
             scene = bpy.context.scene
             # these 2 lines should update the previews enum and set the first result as active.
             wm = bpy.context.window_manager
             asset_type = thread[2]
-            if asset_type == 'model':
-                props = scene.blenderkit_models
-                # json_filepath = os.path.join(icons_dir, 'model_searchresult.json')
-            if asset_type == 'scene':
-                props = scene.blenderkit_scene
-                # json_filepath = os.path.join(icons_dir, 'scene_searchresult.json')
-            if asset_type == 'hdr':
-                props = scene.blenderkit_HDR
-                # json_filepath = os.path.join(icons_dir, 'scene_searchresult.json')
-            if asset_type == 'material':
-                props = scene.blenderkit_mat
-                # json_filepath = os.path.join(icons_dir, 'material_searchresult.json')
-            if asset_type == 'brush':
-                props = scene.blenderkit_brush
-                # json_filepath = os.path.join(icons_dir, 'brush_searchresult.json')
+
+            props = utils.get_search_props()
             search_name = f'bkit {asset_type} search'
 
-            wm[search_name] = []
+            if not thread[0].params.get('get_next'):
+                # wm[search_name] = []
+                result_field = []
+            else:
+                result_field = []
+                for r in wm[search_name]:
+                    result_field.append(r.to_dict())
 
             global reports_queue
 
@@ -427,21 +416,19 @@ def search_timer():
                 return .2
 
             rdata = thread[0].result
-            result_field = []
+
+
 
             ok, error = check_errors(rdata)
             if ok:
                 ui_props = bpy.context.scene.blenderkitUI
 
-                if not ui_props.assetbar_on:
-                    bpy.ops.object.run_assetbar_fix_context()
-
-
-
-                for r in rdata['results']:
+                orig_len = len(result_field)
+                for ri, r in enumerate(rdata['results']):
                     asset_data = parse_result(r)
                     if asset_data != None:
                         result_field.append(asset_data)
+                        load_preview(asset_data,ri + orig_len)
 
                 # Get ratings from BlenderKit server
                 user_preferences = bpy.context.preferences.addons['blenderkit'].preferences
@@ -455,32 +442,74 @@ def search_timer():
 
                 wm[search_name] = result_field
                 wm['search results'] = result_field
-                wm[search_name + ' orig'] = copy.deepcopy(rdata)
-                wm['search results orig'] = wm[search_name + ' orig']
 
-                load_previews()
+                #rdata=['results']=[]
+                wm[search_name + ' orig'] = rdata
+                wm['search results orig'] = rdata
+
+                # load_previews()
                 if len(result_field) < ui_props.scrolloffset or not (thread[0].params.get('get_next')):
                     # jump back
                     ui_props.scrolloffset = 0
-                props.is_searching = False
              

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-extensions-cvs mailing list