2022-02-11 09:07:11 +11:00
|
|
|
# SPDX-License-Identifier: GPL-2.0-or-later
|
2009-10-31 20:16:59 +00:00
|
|
|
|
2010-01-22 02:04:25 +00:00
|
|
|
"""
|
2010-07-15 20:02:53 +00:00
|
|
|
This module contains utility functions specific to blender but
|
2012-07-04 15:04:38 +00:00
|
|
|
not associated with blenders internal data.
|
2010-01-22 02:04:25 +00:00
|
|
|
"""
|
|
|
|
|
2011-07-31 03:15:37 +00:00
|
|
|
__all__ = (
|
|
|
|
"blend_paths",
|
2014-02-25 16:18:10 +11:00
|
|
|
"escape_identifier",
|
2021-11-10 01:14:56 +11:00
|
|
|
"flip_name",
|
2020-12-10 14:09:29 +11:00
|
|
|
"unescape_identifier",
|
2018-11-12 14:53:08 +01:00
|
|
|
"keyconfig_init",
|
2011-07-31 03:15:37 +00:00
|
|
|
"keyconfig_set",
|
|
|
|
"load_scripts",
|
|
|
|
"modules_from_path",
|
|
|
|
"preset_find",
|
|
|
|
"preset_paths",
|
|
|
|
"refresh_script_paths",
|
2017-03-25 09:29:51 +11:00
|
|
|
"app_template_paths",
|
2011-07-31 03:15:37 +00:00
|
|
|
"register_class",
|
2012-08-25 14:07:51 +00:00
|
|
|
"register_manual_map",
|
2012-08-25 14:18:54 +00:00
|
|
|
"unregister_manual_map",
|
2017-09-05 00:22:31 +10:00
|
|
|
"register_classes_factory",
|
2017-07-25 17:34:34 +10:00
|
|
|
"register_submodule_factory",
|
2019-03-14 14:15:29 +11:00
|
|
|
"register_tool",
|
2013-02-24 08:50:55 +00:00
|
|
|
"make_rna_paths",
|
2012-08-25 14:18:54 +00:00
|
|
|
"manual_map",
|
2023-02-10 11:01:02 +11:00
|
|
|
"manual_language_code",
|
2015-05-11 16:29:12 +02:00
|
|
|
"previews",
|
2011-07-31 03:15:37 +00:00
|
|
|
"resource_path",
|
2012-07-29 01:02:25 +00:00
|
|
|
"script_path_user",
|
|
|
|
"script_path_pref",
|
2011-07-31 03:15:37 +00:00
|
|
|
"script_paths",
|
|
|
|
"smpte_from_frame",
|
|
|
|
"smpte_from_seconds",
|
2014-06-17 16:03:40 +02:00
|
|
|
"units",
|
2011-07-31 03:15:37 +00:00
|
|
|
"unregister_class",
|
2019-03-14 14:15:29 +11:00
|
|
|
"unregister_tool",
|
2011-07-31 03:15:37 +00:00
|
|
|
"user_resource",
|
2018-11-18 11:49:03 +11:00
|
|
|
"execfile",
|
2017-03-26 21:51:12 +11:00
|
|
|
)
|
2011-07-31 03:15:37 +00:00
|
|
|
|
2014-02-25 16:18:10 +11:00
|
|
|
from _bpy import (
|
2017-03-26 21:51:12 +11:00
|
|
|
_utils_units as units,
|
|
|
|
blend_paths,
|
|
|
|
escape_identifier,
|
2021-11-10 01:14:56 +11:00
|
|
|
flip_name,
|
2020-12-10 14:09:29 +11:00
|
|
|
unescape_identifier,
|
2017-03-26 21:51:12 +11:00
|
|
|
register_class,
|
|
|
|
resource_path,
|
|
|
|
script_paths as _bpy_script_paths,
|
|
|
|
unregister_class,
|
|
|
|
user_resource as _user_resource,
|
2019-07-23 16:23:56 +10:00
|
|
|
system_resource,
|
2017-03-26 21:51:12 +11:00
|
|
|
)
|
2010-02-14 23:33:18 +00:00
|
|
|
|
2010-11-20 02:56:58 +00:00
|
|
|
import bpy as _bpy
|
|
|
|
import os as _os
|
|
|
|
import sys as _sys
|
2010-09-07 15:17:42 +00:00
|
|
|
|
2011-03-18 20:57:32 +00:00
|
|
|
import addon_utils as _addon_utils
|
2011-01-01 07:20:34 +00:00
|
|
|
|
2018-12-21 12:47:44 +11:00
|
|
|
_preferences = _bpy.context.preferences
|
2017-07-25 20:50:12 +10:00
|
|
|
_is_factory_startup = _bpy.app.factory_startup
|
2011-02-25 16:06:14 +00:00
|
|
|
|
2022-09-21 11:59:16 +10:00
|
|
|
# Directories added to the start of `sys.path` for all of Blender's "scripts" directories.
|
|
|
|
_script_module_dirs = "startup", "modules"
|
|
|
|
|
|
|
|
# Base scripts, this points to the directory containing: "modules" & "startup" (see `_script_module_dirs`).
|
2023-02-21 16:39:58 +01:00
|
|
|
# In Blender's code-base this is `./scripts`.
|
2022-09-21 11:59:16 +10:00
|
|
|
#
|
2023-03-24 08:34:21 -04:00
|
|
|
# NOTE: in virtually all cases this should match `BLENDER_SYSTEM_SCRIPTS` as this script is itself a system script,
|
2022-09-21 11:59:16 +10:00
|
|
|
# it must be in the `BLENDER_SYSTEM_SCRIPTS` by definition and there is no need for a look-up from `_bpy_script_paths`.
|
|
|
|
_script_base_dir = _os.path.dirname(_os.path.dirname(_os.path.dirname(_os.path.dirname(__file__))))
|
|
|
|
|
2012-09-26 21:19:51 +00:00
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
def execfile(filepath, *, mod=None):
|
2021-02-19 11:13:35 +11:00
|
|
|
"""
|
|
|
|
Execute a file path as a Python script.
|
|
|
|
|
|
|
|
:arg filepath: Path of the script to execute.
|
|
|
|
:type filepath: string
|
|
|
|
:arg mod: Optional cached module, the result of a previous execution.
|
|
|
|
:type mod: Module or None
|
|
|
|
:return: The module which can be passed back in as ``mod``.
|
|
|
|
:rtype: ModuleType
|
|
|
|
"""
|
2018-11-18 11:49:03 +11:00
|
|
|
|
|
|
|
import importlib.util
|
2021-02-19 11:13:35 +11:00
|
|
|
mod_name = "__main__"
|
|
|
|
mod_spec = importlib.util.spec_from_file_location(mod_name, filepath)
|
2018-11-18 11:49:03 +11:00
|
|
|
if mod is None:
|
|
|
|
mod = importlib.util.module_from_spec(mod_spec)
|
2021-02-19 11:13:35 +11:00
|
|
|
|
|
|
|
# While the module name is not added to `sys.modules`, it's important to temporarily
|
|
|
|
# include this so statements such as `sys.modules[cls.__module__].__dict__` behave as expected.
|
|
|
|
# See: https://bugs.python.org/issue9499 for details.
|
|
|
|
modules = _sys.modules
|
|
|
|
mod_orig = modules.get(mod_name, None)
|
|
|
|
modules[mod_name] = mod
|
|
|
|
|
2021-11-16 18:44:04 -05:00
|
|
|
# No error suppression, just ensure `sys.modules[mod_name]` is properly restored in the case of an error.
|
2021-02-19 11:13:35 +11:00
|
|
|
try:
|
|
|
|
mod_spec.loader.exec_module(mod)
|
|
|
|
finally:
|
|
|
|
if mod_orig is None:
|
|
|
|
modules.pop(mod_name, None)
|
|
|
|
else:
|
|
|
|
modules[mod_name] = mod_orig
|
|
|
|
|
2018-11-18 11:49:03 +11:00
|
|
|
return mod
|
|
|
|
|
|
|
|
|
2010-02-14 23:33:18 +00:00
|
|
|
def _test_import(module_name, loaded_modules):
|
2012-03-31 00:59:17 +00:00
|
|
|
use_time = _bpy.app.debug_python
|
2011-02-27 14:16:32 +00:00
|
|
|
|
2010-02-14 23:33:18 +00:00
|
|
|
if module_name in loaded_modules:
|
|
|
|
return None
|
|
|
|
if "." in module_name:
|
2011-07-31 03:15:37 +00:00
|
|
|
print("Ignoring '%s', can't import files containing "
|
2011-09-19 14:00:42 +00:00
|
|
|
"multiple periods" % module_name)
|
2010-02-14 23:33:18 +00:00
|
|
|
return None
|
|
|
|
|
2011-02-27 14:16:32 +00:00
|
|
|
if use_time:
|
|
|
|
import time
|
|
|
|
t = time.time()
|
|
|
|
|
2010-02-14 23:33:18 +00:00
|
|
|
try:
|
2010-02-16 13:13:22 +00:00
|
|
|
mod = __import__(module_name)
|
2010-02-14 23:33:18 +00:00
|
|
|
except:
|
2011-02-27 14:16:32 +00:00
|
|
|
import traceback
|
2010-02-14 23:33:18 +00:00
|
|
|
traceback.print_exc()
|
|
|
|
return None
|
|
|
|
|
2011-02-27 14:16:32 +00:00
|
|
|
if use_time:
|
2010-02-16 13:13:22 +00:00
|
|
|
print("time %s %.4f" % (module_name, time.time() - t))
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2010-09-07 15:17:42 +00:00
|
|
|
loaded_modules.add(mod.__name__) # should match mod.__name__ too
|
2010-02-16 13:13:22 +00:00
|
|
|
return mod
|
2010-02-14 23:33:18 +00:00
|
|
|
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2021-02-16 15:51:04 +11:00
|
|
|
# Check before adding paths as reloading would add twice.
|
|
|
|
|
|
|
|
# Storing and restoring the full `sys.path` is risky as this may be intentionally modified
|
|
|
|
# by technical users/developers.
|
|
|
|
#
|
|
|
|
# Instead, track which paths have been added, clearing them before refreshing.
|
|
|
|
# This supports the case of loading a new preferences file which may reset scripts path.
|
|
|
|
_sys_path_ensure_paths = set()
|
|
|
|
|
2021-07-06 12:05:27 +10:00
|
|
|
|
2019-08-15 15:53:11 +10:00
|
|
|
def _sys_path_ensure_prepend(path):
|
|
|
|
if path not in _sys.path:
|
2010-09-13 04:52:56 +00:00
|
|
|
_sys.path.insert(0, path)
|
2021-02-16 15:51:04 +11:00
|
|
|
_sys_path_ensure_paths.add(path)
|
2010-09-13 04:52:56 +00:00
|
|
|
|
|
|
|
|
2019-08-15 15:53:11 +10:00
|
|
|
def _sys_path_ensure_append(path):
|
|
|
|
if path not in _sys.path:
|
|
|
|
_sys.path.append(path)
|
2021-02-16 15:51:04 +11:00
|
|
|
_sys_path_ensure_paths.add(path)
|
2019-08-15 15:53:11 +10:00
|
|
|
|
|
|
|
|
2010-02-14 23:33:18 +00:00
|
|
|
def modules_from_path(path, loaded_modules):
|
|
|
|
"""
|
|
|
|
Load all modules in a path and return them as a list.
|
2010-02-16 15:01:34 +00:00
|
|
|
|
|
|
|
:arg path: this path is scanned for scripts and packages.
|
|
|
|
:type path: string
|
2011-07-31 03:15:37 +00:00
|
|
|
:arg loaded_modules: already loaded module names, files matching these
|
|
|
|
names will be ignored.
|
2010-02-16 15:01:34 +00:00
|
|
|
:type loaded_modules: set
|
|
|
|
:return: all loaded modules.
|
|
|
|
:rtype: list
|
2010-02-14 23:33:18 +00:00
|
|
|
"""
|
|
|
|
modules = []
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2019-03-17 21:13:25 +11:00
|
|
|
for mod_name, _mod_path in _bpy.path.module_names(path):
|
2010-09-08 04:55:37 +00:00
|
|
|
mod = _test_import(mod_name, loaded_modules)
|
2010-02-14 23:33:18 +00:00
|
|
|
if mod:
|
|
|
|
modules.append(mod)
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2010-02-14 23:33:18 +00:00
|
|
|
return modules
|
2010-09-07 15:17:42 +00:00
|
|
|
|
|
|
|
|
|
|
|
_global_loaded_modules = [] # store loaded module names for reloading.
|
|
|
|
import bpy_types as _bpy_types # keep for comparisons, never ever reload this.
|
2010-02-15 10:54:51 +00:00
|
|
|
|
2010-02-14 23:33:18 +00:00
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
def load_scripts(*, reload_scripts=False, refresh_scripts=False):
|
2010-02-16 15:01:34 +00:00
|
|
|
"""
|
|
|
|
Load scripts and run each modules register function.
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2011-07-31 03:15:37 +00:00
|
|
|
:arg reload_scripts: Causes all scripts to have their unregister method
|
|
|
|
called before loading.
|
2010-02-16 15:01:34 +00:00
|
|
|
:type reload_scripts: bool
|
2011-07-31 03:15:37 +00:00
|
|
|
:arg refresh_scripts: only load scripts which are not already loaded
|
|
|
|
as modules.
|
2010-02-16 15:01:34 +00:00
|
|
|
:type refresh_scripts: bool
|
|
|
|
"""
|
2017-03-26 21:51:12 +11:00
|
|
|
use_time = use_class_register_check = _bpy.app.debug_python
|
2017-07-25 20:50:12 +10:00
|
|
|
use_user = not _is_factory_startup
|
2010-01-28 11:48:06 +00:00
|
|
|
|
2011-02-28 04:37:24 +00:00
|
|
|
if use_time:
|
|
|
|
import time
|
|
|
|
t_main = time.time()
|
2010-01-28 11:48:06 +00:00
|
|
|
|
|
|
|
loaded_modules = set()
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2010-02-15 10:54:51 +00:00
|
|
|
if refresh_scripts:
|
|
|
|
original_modules = _sys.modules.values()
|
2010-09-07 15:17:42 +00:00
|
|
|
|
2010-08-03 03:53:36 +00:00
|
|
|
if reload_scripts:
|
2011-10-17 06:58:07 +00:00
|
|
|
# just unload, don't change user defaults, this means we can sync
|
2011-07-31 03:15:37 +00:00
|
|
|
# to reload. note that they will only actually reload of the
|
2011-10-17 06:58:07 +00:00
|
|
|
# modification time changes. This `won't` work for packages so...
|
2011-07-31 03:15:37 +00:00
|
|
|
# its not perfect.
|
2018-12-21 12:47:44 +11:00
|
|
|
for module_name in [ext.module for ext in _preferences.addons]:
|
2015-06-14 05:12:45 +10:00
|
|
|
_addon_utils.disable(module_name)
|
2010-09-13 04:52:56 +00:00
|
|
|
|
2010-08-03 03:53:36 +00:00
|
|
|
def register_module_call(mod):
|
|
|
|
register = getattr(mod, "register", None)
|
|
|
|
if register:
|
|
|
|
try:
|
|
|
|
register()
|
|
|
|
except:
|
2011-02-27 14:16:32 +00:00
|
|
|
import traceback
|
2010-08-03 03:53:36 +00:00
|
|
|
traceback.print_exc()
|
|
|
|
else:
|
2011-07-31 03:15:37 +00:00
|
|
|
print("\nWarning! '%s' has no register function, "
|
2011-09-19 14:00:42 +00:00
|
|
|
"this is now a requirement for registerable scripts" %
|
2011-07-31 03:15:37 +00:00
|
|
|
mod.__file__)
|
2010-08-03 03:53:36 +00:00
|
|
|
|
|
|
|
def unregister_module_call(mod):
|
2010-08-02 02:55:12 +00:00
|
|
|
unregister = getattr(mod, "unregister", None)
|
|
|
|
if unregister:
|
|
|
|
try:
|
|
|
|
unregister()
|
|
|
|
except:
|
2011-02-27 14:16:32 +00:00
|
|
|
import traceback
|
2010-08-02 02:55:12 +00:00
|
|
|
traceback.print_exc()
|
2010-08-03 03:53:36 +00:00
|
|
|
|
2010-02-15 10:54:51 +00:00
|
|
|
def test_reload(mod):
|
2015-01-23 12:37:58 +11:00
|
|
|
import importlib
|
2010-02-15 10:54:51 +00:00
|
|
|
# reloading this causes internal errors
|
|
|
|
# because the classes from this module are stored internally
|
|
|
|
# possibly to refresh internal references too but for now, best not to.
|
|
|
|
if mod == _bpy_types:
|
|
|
|
return mod
|
|
|
|
|
2010-01-28 11:48:06 +00:00
|
|
|
try:
|
2015-01-23 12:37:58 +11:00
|
|
|
return importlib.reload(mod)
|
2010-01-28 11:48:06 +00:00
|
|
|
except:
|
2011-02-27 14:16:32 +00:00
|
|
|
import traceback
|
2010-01-28 11:48:06 +00:00
|
|
|
traceback.print_exc()
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2010-02-14 23:33:18 +00:00
|
|
|
def test_register(mod):
|
2010-02-15 10:54:51 +00:00
|
|
|
|
|
|
|
if refresh_scripts and mod in original_modules:
|
|
|
|
return
|
|
|
|
|
2010-02-14 23:33:18 +00:00
|
|
|
if reload_scripts and mod:
|
|
|
|
print("Reloading:", mod)
|
|
|
|
mod = test_reload(mod)
|
|
|
|
|
|
|
|
if mod:
|
2010-08-03 03:53:36 +00:00
|
|
|
register_module_call(mod)
|
|
|
|
_global_loaded_modules.append(mod.__name__)
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2010-01-28 11:48:06 +00:00
|
|
|
if reload_scripts:
|
2010-06-09 19:12:03 +00:00
|
|
|
|
2010-08-03 03:53:36 +00:00
|
|
|
# module names -> modules
|
2011-07-31 03:15:37 +00:00
|
|
|
_global_loaded_modules[:] = [_sys.modules[mod_name]
|
|
|
|
for mod_name in _global_loaded_modules]
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2010-02-15 10:54:51 +00:00
|
|
|
# loop over and unload all scripts
|
2010-08-03 03:53:36 +00:00
|
|
|
_global_loaded_modules.reverse()
|
|
|
|
for mod in _global_loaded_modules:
|
|
|
|
unregister_module_call(mod)
|
2010-06-01 08:15:43 +00:00
|
|
|
|
2010-08-03 03:53:36 +00:00
|
|
|
for mod in _global_loaded_modules:
|
|
|
|
test_reload(mod)
|
2010-06-01 08:15:43 +00:00
|
|
|
|
2012-11-14 09:45:15 +00:00
|
|
|
del _global_loaded_modules[:]
|
2010-02-15 10:54:51 +00:00
|
|
|
|
2012-12-20 03:56:22 +00:00
|
|
|
from bpy_restrict_state import RestrictBlend
|
|
|
|
|
|
|
|
with RestrictBlend():
|
2017-07-25 20:50:12 +10:00
|
|
|
for base_path in script_paths(use_user=use_user):
|
2012-12-20 03:56:22 +00:00
|
|
|
for path_subdir in _script_module_dirs:
|
|
|
|
path = _os.path.join(base_path, path_subdir)
|
|
|
|
if _os.path.isdir(path):
|
2019-08-15 15:53:11 +10:00
|
|
|
_sys_path_ensure_prepend(path)
|
2012-12-20 03:56:22 +00:00
|
|
|
|
2019-06-13 10:03:06 +10:00
|
|
|
# Only add to 'sys.modules' unless this is 'startup'.
|
|
|
|
if path_subdir == "startup":
|
|
|
|
for mod in modules_from_path(path, loaded_modules):
|
|
|
|
test_register(mod)
|
2010-02-15 10:54:51 +00:00
|
|
|
|
2017-03-25 09:29:51 +11:00
|
|
|
# load template (if set)
|
|
|
|
if any(_bpy.utils.app_template_paths()):
|
|
|
|
import bl_app_template_utils
|
|
|
|
bl_app_template_utils.reset(reload_scripts=reload_scripts)
|
|
|
|
del bl_app_template_utils
|
|
|
|
|
2011-03-29 04:16:55 +00:00
|
|
|
# deal with addons separately
|
2015-01-23 16:20:37 +11:00
|
|
|
_initialize = getattr(_addon_utils, "_initialize", None)
|
|
|
|
if _initialize is not None:
|
|
|
|
# first time, use fast-path
|
|
|
|
_initialize()
|
|
|
|
del _addon_utils._initialize
|
|
|
|
else:
|
2015-11-16 09:41:42 +11:00
|
|
|
_addon_utils.reset_all(reload_scripts=reload_scripts)
|
2015-01-23 16:20:37 +11:00
|
|
|
del _initialize
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2010-02-17 19:50:42 +00:00
|
|
|
if reload_scripts:
|
2020-09-14 17:50:01 +10:00
|
|
|
_bpy.context.window_manager.tag_script_reload()
|
|
|
|
|
2010-02-17 19:50:42 +00:00
|
|
|
import gc
|
|
|
|
print("gc.collect() -> %d" % gc.collect())
|
2010-01-28 11:48:06 +00:00
|
|
|
|
2011-02-28 04:37:24 +00:00
|
|
|
if use_time:
|
2010-07-26 09:09:53 +00:00
|
|
|
print("Python Script Load Time %.4f" % (time.time() - t_main))
|
2009-12-13 13:59:16 +00:00
|
|
|
|
2017-03-26 11:14:47 +11:00
|
|
|
if use_class_register_check:
|
|
|
|
for cls in _bpy.types.bpy_struct.__subclasses__():
|
|
|
|
if getattr(cls, "is_registered", False):
|
|
|
|
for subcls in cls.__subclasses__():
|
|
|
|
if not subcls.is_registered:
|
|
|
|
print(
|
|
|
|
"Warning, unregistered class: %s(%s)" %
|
|
|
|
(subcls.__name__, cls.__name__)
|
|
|
|
)
|
|
|
|
|
2009-11-28 20:50:31 +00:00
|
|
|
|
2012-07-29 01:02:25 +00:00
|
|
|
def script_path_user():
|
|
|
|
"""returns the env var and falls back to home dir or None"""
|
2012-06-29 08:33:13 +00:00
|
|
|
path = _user_resource('SCRIPTS')
|
2012-07-29 01:02:25 +00:00
|
|
|
return _os.path.normpath(path) if path else None
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2012-07-29 01:02:25 +00:00
|
|
|
|
|
|
|
def script_path_pref():
|
|
|
|
"""returns the user preference or None"""
|
2018-12-21 12:47:44 +11:00
|
|
|
path = _preferences.filepaths.script_directory
|
2012-07-29 01:02:25 +00:00
|
|
|
return _os.path.normpath(path) if path else None
|
2009-12-13 13:59:16 +00:00
|
|
|
|
2010-02-22 23:32:58 +00:00
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
def script_paths(*, subdir=None, user_pref=True, check_all=False, use_user=True):
|
2010-01-22 02:04:25 +00:00
|
|
|
"""
|
2011-05-02 17:29:30 +00:00
|
|
|
Returns a list of valid script paths.
|
|
|
|
|
|
|
|
:arg subdir: Optional subdir.
|
|
|
|
:type subdir: string
|
|
|
|
:arg user_pref: Include the user preference script path.
|
|
|
|
:type user_pref: bool
|
2022-09-21 11:59:16 +10:00
|
|
|
:arg check_all: Include local, user and system paths rather just the paths Blender uses.
|
2011-11-24 19:36:12 +00:00
|
|
|
:type check_all: bool
|
2011-05-02 17:29:30 +00:00
|
|
|
:return: script paths.
|
|
|
|
:rtype: list
|
2010-01-22 02:04:25 +00:00
|
|
|
"""
|
2010-02-22 23:32:58 +00:00
|
|
|
|
2022-09-29 17:12:10 +10:00
|
|
|
if check_all or use_user:
|
|
|
|
path_system, path_user = _bpy_script_paths()
|
2011-05-02 17:29:30 +00:00
|
|
|
|
2022-09-29 17:12:10 +10:00
|
|
|
base_paths = []
|
2017-07-27 22:22:26 +10:00
|
|
|
|
2016-05-14 03:25:06 +10:00
|
|
|
if check_all:
|
2022-09-29 17:12:10 +10:00
|
|
|
# Order: 'LOCAL', 'USER', 'SYSTEM' (where user is optional).
|
|
|
|
if path_local := resource_path('LOCAL'):
|
|
|
|
base_paths.append(_os.path.join(path_local, "scripts"))
|
2017-07-25 20:50:12 +10:00
|
|
|
if use_user:
|
2022-09-29 17:12:10 +10:00
|
|
|
base_paths.append(path_user)
|
|
|
|
base_paths.append(path_system) # Same as: `system_resource('SCRIPTS')`.
|
|
|
|
|
|
|
|
# Note that `_script_base_dir` may be either:
|
|
|
|
# - `os.path.join(bpy.utils.resource_path('LOCAL'), "scripts")`
|
|
|
|
# - `bpy.utils.system_resource('SCRIPTS')`.
|
|
|
|
# When `check_all` is enabled duplicate paths will be added however
|
|
|
|
# paths are de-duplicated so it wont cause problems.
|
|
|
|
base_paths.append(_script_base_dir)
|
|
|
|
|
|
|
|
if not check_all:
|
|
|
|
if use_user:
|
|
|
|
base_paths.append(path_user)
|
|
|
|
|
|
|
|
if user_pref:
|
|
|
|
base_paths.append(script_path_pref())
|
|
|
|
|
|
|
|
scripts = []
|
|
|
|
for path in base_paths:
|
|
|
|
if not path:
|
|
|
|
continue
|
|
|
|
|
|
|
|
path = _os.path.normpath(path)
|
|
|
|
if subdir is not None:
|
|
|
|
path = _os.path.join(path, subdir)
|
|
|
|
|
|
|
|
if path in scripts:
|
|
|
|
continue
|
|
|
|
if not _os.path.isdir(path):
|
|
|
|
continue
|
|
|
|
scripts.append(path)
|
|
|
|
|
|
|
|
return scripts
|
2009-11-22 11:23:19 +00:00
|
|
|
|
|
|
|
|
2011-05-04 08:44:08 +00:00
|
|
|
def refresh_script_paths():
|
|
|
|
"""
|
|
|
|
Run this after creating new script paths to update sys.path
|
|
|
|
"""
|
|
|
|
|
2021-02-16 15:51:04 +11:00
|
|
|
for path in _sys_path_ensure_paths:
|
|
|
|
try:
|
|
|
|
_sys.path.remove(path)
|
|
|
|
except ValueError:
|
|
|
|
pass
|
|
|
|
_sys_path_ensure_paths.clear()
|
|
|
|
|
2011-05-04 08:44:08 +00:00
|
|
|
for base_path in script_paths():
|
|
|
|
for path_subdir in _script_module_dirs:
|
|
|
|
path = _os.path.join(base_path, path_subdir)
|
|
|
|
if _os.path.isdir(path):
|
2019-08-15 15:53:11 +10:00
|
|
|
_sys_path_ensure_prepend(path)
|
2011-05-04 08:44:08 +00:00
|
|
|
|
|
|
|
for path in _addon_utils.paths():
|
2019-08-15 15:53:11 +10:00
|
|
|
_sys_path_ensure_append(path)
|
2011-05-04 08:44:08 +00:00
|
|
|
path = _os.path.join(path, "modules")
|
|
|
|
if _os.path.isdir(path):
|
2019-08-15 15:53:11 +10:00
|
|
|
_sys_path_ensure_append(path)
|
2011-05-04 08:44:08 +00:00
|
|
|
|
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
def app_template_paths(*, path=None):
|
2017-03-25 09:29:51 +11:00
|
|
|
"""
|
|
|
|
Returns valid application template paths.
|
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
:arg path: Optional subdir.
|
|
|
|
:type path: string
|
2017-03-25 09:29:51 +11:00
|
|
|
:return: app template paths.
|
|
|
|
:rtype: generator
|
|
|
|
"""
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
subdir_args = (path,) if path is not None else ()
|
2020-01-28 14:01:18 +11:00
|
|
|
# Note: keep in sync with: Blender's 'BKE_appdir_app_template_any'.
|
|
|
|
# Uses 'BLENDER_USER_SCRIPTS', 'BLENDER_SYSTEM_SCRIPTS'
|
|
|
|
# ... in this case 'system' accounts for 'local' too.
|
|
|
|
for resource_fn, module_name in (
|
|
|
|
(_user_resource, "bl_app_templates_user"),
|
|
|
|
(system_resource, "bl_app_templates_system"),
|
2017-09-15 05:46:43 +10:00
|
|
|
):
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
path_test = resource_fn('SCRIPTS', path=_os.path.join("startup", module_name, *subdir_args))
|
|
|
|
if path_test and _os.path.isdir(path_test):
|
|
|
|
yield path_test
|
2017-03-25 09:29:51 +11:00
|
|
|
|
|
|
|
|
2009-11-22 11:23:19 +00:00
|
|
|
def preset_paths(subdir):
|
2010-09-13 04:52:56 +00:00
|
|
|
"""
|
2010-08-02 02:55:12 +00:00
|
|
|
Returns a list of paths for a specific preset.
|
2011-07-20 15:33:27 +00:00
|
|
|
|
|
|
|
:arg subdir: preset subdirectory (must not be an absolute path).
|
|
|
|
:type subdir: string
|
|
|
|
:return: script paths.
|
|
|
|
:rtype: list
|
2010-09-13 04:52:56 +00:00
|
|
|
"""
|
2010-09-15 13:41:38 +00:00
|
|
|
dirs = []
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
for path in script_paths(subdir="presets", check_all=True):
|
2010-09-15 13:41:38 +00:00
|
|
|
directory = _os.path.join(path, subdir)
|
2011-07-20 15:33:27 +00:00
|
|
|
if not directory.startswith(path):
|
|
|
|
raise Exception("invalid subdir given %r" % subdir)
|
|
|
|
elif _os.path.isdir(directory):
|
2010-09-15 13:41:38 +00:00
|
|
|
dirs.append(directory)
|
2011-12-30 08:39:40 +00:00
|
|
|
|
|
|
|
# Find addons preset paths
|
2012-06-10 00:22:18 +00:00
|
|
|
for path in _addon_utils.paths():
|
2011-12-30 08:39:40 +00:00
|
|
|
directory = _os.path.join(path, "presets", subdir)
|
|
|
|
if _os.path.isdir(directory):
|
|
|
|
dirs.append(directory)
|
|
|
|
|
2010-09-15 13:41:38 +00:00
|
|
|
return dirs
|
2010-05-10 20:41:01 +00:00
|
|
|
|
2019-10-31 18:01:58 +11:00
|
|
|
|
2019-10-30 19:16:53 +01:00
|
|
|
def is_path_builtin(path):
|
|
|
|
"""
|
2019-10-31 18:01:58 +11:00
|
|
|
Returns True if the path is one of the built-in paths used by Blender.
|
2019-10-30 19:16:53 +01:00
|
|
|
|
2019-10-31 18:01:58 +11:00
|
|
|
:arg path: Path you want to check if it is in the built-in settings directory
|
|
|
|
:type path: str
|
|
|
|
:rtype: bool
|
2019-10-30 19:16:53 +01:00
|
|
|
"""
|
2022-04-05 22:21:13 +02:00
|
|
|
# Note that this function isn't optimized for speed,
|
2019-10-31 18:01:58 +11:00
|
|
|
# it's intended to be used to check if it's OK to remove presets.
|
|
|
|
#
|
|
|
|
# If this is used in a draw-loop for example, we could cache some of the values.
|
2019-10-30 19:16:53 +01:00
|
|
|
user_path = resource_path('USER')
|
|
|
|
|
|
|
|
for res in ('SYSTEM', 'LOCAL'):
|
|
|
|
parent_path = resource_path(res)
|
|
|
|
if not parent_path or parent_path == user_path:
|
|
|
|
# Make sure that the current path is not empty string and that it is
|
2019-10-31 18:01:58 +11:00
|
|
|
# not the same as the user config path. IE "~/.config/blender" on Linux
|
2019-10-30 19:16:53 +01:00
|
|
|
# This can happen on portable installs.
|
|
|
|
continue
|
|
|
|
|
2019-11-01 17:48:57 +01:00
|
|
|
try:
|
|
|
|
if _os.path.samefile(
|
|
|
|
_os.path.commonpath([parent_path]),
|
|
|
|
_os.path.commonpath([parent_path, path])
|
|
|
|
):
|
|
|
|
return True
|
|
|
|
except FileNotFoundError:
|
2020-01-27 15:10:48 +01:00
|
|
|
# The path we tried to look up doesn't exist.
|
|
|
|
pass
|
|
|
|
except ValueError:
|
|
|
|
# Happens on Windows when paths don't have the same drive.
|
2019-11-01 17:48:57 +01:00
|
|
|
pass
|
2019-10-30 19:16:53 +01:00
|
|
|
|
|
|
|
return False
|
2010-05-10 20:41:01 +00:00
|
|
|
|
2019-10-31 18:01:58 +11:00
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
def smpte_from_seconds(time, *, fps=None, fps_base=None):
|
2010-09-13 04:52:56 +00:00
|
|
|
"""
|
2015-08-03 13:32:58 +10:00
|
|
|
Returns an SMPTE formatted string from the *time*:
|
|
|
|
``HH:MM:SS:FF``.
|
2010-05-10 20:41:01 +00:00
|
|
|
|
2019-06-19 10:49:37 -07:00
|
|
|
If *fps* and *fps_base* are not given the current scene is used.
|
2010-05-10 20:41:01 +00:00
|
|
|
|
2015-08-03 13:32:58 +10:00
|
|
|
:arg time: time in seconds.
|
|
|
|
:type time: int, float or ``datetime.timedelta``.
|
|
|
|
:return: the frame string.
|
|
|
|
:rtype: string
|
|
|
|
"""
|
2010-05-10 20:41:01 +00:00
|
|
|
|
2019-06-19 10:49:37 -07:00
|
|
|
return smpte_from_frame(
|
|
|
|
time_to_frame(time, fps=fps, fps_base=fps_base),
|
|
|
|
fps=fps,
|
|
|
|
fps_base=fps_base
|
|
|
|
)
|
2010-05-16 12:15:04 +00:00
|
|
|
|
2010-05-10 20:41:01 +00:00
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
def smpte_from_frame(frame, *, fps=None, fps_base=None):
|
2010-09-13 04:52:56 +00:00
|
|
|
"""
|
2015-08-03 13:32:58 +10:00
|
|
|
Returns an SMPTE formatted string from the *frame*:
|
|
|
|
``HH:MM:SS:FF``.
|
2010-05-10 20:41:01 +00:00
|
|
|
|
2010-09-08 04:55:37 +00:00
|
|
|
If *fps* and *fps_base* are not given the current scene is used.
|
2012-05-28 16:06:38 +00:00
|
|
|
|
2015-08-03 13:32:58 +10:00
|
|
|
:arg frame: frame number.
|
|
|
|
:type frame: int or float.
|
|
|
|
:return: the frame string.
|
|
|
|
:rtype: string
|
2010-09-13 04:52:56 +00:00
|
|
|
"""
|
2010-05-10 20:41:01 +00:00
|
|
|
|
|
|
|
if fps is None:
|
|
|
|
fps = _bpy.context.scene.render.fps
|
|
|
|
|
|
|
|
if fps_base is None:
|
|
|
|
fps_base = _bpy.context.scene.render.fps_base
|
|
|
|
|
2019-06-19 10:49:37 -07:00
|
|
|
fps = fps / fps_base
|
2015-08-03 13:32:58 +10:00
|
|
|
sign = "-" if frame < 0 else ""
|
2019-06-19 10:49:37 -07:00
|
|
|
frame = abs(frame)
|
2015-08-03 13:32:58 +10:00
|
|
|
|
|
|
|
return (
|
|
|
|
"%s%02d:%02d:%02d:%02d" % (
|
2018-07-03 22:35:37 +02:00
|
|
|
sign,
|
|
|
|
int(frame / (3600 * fps)), # HH
|
|
|
|
int((frame / (60 * fps)) % 60), # MM
|
|
|
|
int((frame / fps) % 60), # SS
|
|
|
|
int(frame % fps), # FF
|
2015-08-03 13:32:58 +10:00
|
|
|
))
|
2010-09-13 04:52:56 +00:00
|
|
|
|
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
def time_from_frame(frame, *, fps=None, fps_base=None):
|
2012-05-28 16:06:38 +00:00
|
|
|
"""
|
|
|
|
Returns the time from a frame number .
|
|
|
|
|
|
|
|
If *fps* and *fps_base* are not given the current scene is used.
|
|
|
|
|
|
|
|
:arg frame: number.
|
2015-08-03 13:32:58 +10:00
|
|
|
:type frame: int or float.
|
2012-05-28 16:06:38 +00:00
|
|
|
:return: the time in seconds.
|
2014-08-26 10:57:21 +10:00
|
|
|
:rtype: datetime.timedelta
|
2012-05-28 16:06:38 +00:00
|
|
|
"""
|
|
|
|
|
|
|
|
if fps is None:
|
|
|
|
fps = _bpy.context.scene.render.fps
|
|
|
|
|
|
|
|
if fps_base is None:
|
|
|
|
fps_base = _bpy.context.scene.render.fps_base
|
|
|
|
|
2019-06-19 10:49:37 -07:00
|
|
|
fps = fps / fps_base
|
|
|
|
|
2012-05-28 16:06:38 +00:00
|
|
|
from datetime import timedelta
|
|
|
|
|
2019-06-19 10:49:37 -07:00
|
|
|
return timedelta(0, frame / fps)
|
2012-05-28 16:06:38 +00:00
|
|
|
|
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
def time_to_frame(time, *, fps=None, fps_base=None):
|
2012-05-28 16:06:38 +00:00
|
|
|
"""
|
|
|
|
Returns a float frame number from a time given in seconds or
|
2014-08-26 10:57:21 +10:00
|
|
|
as a datetime.timedelta object.
|
2012-05-28 16:06:38 +00:00
|
|
|
|
|
|
|
If *fps* and *fps_base* are not given the current scene is used.
|
|
|
|
|
|
|
|
:arg time: time in seconds.
|
2015-08-03 13:32:58 +10:00
|
|
|
:type time: number or a ``datetime.timedelta`` object
|
2012-05-28 16:06:38 +00:00
|
|
|
:return: the frame.
|
|
|
|
:rtype: float
|
|
|
|
"""
|
|
|
|
|
|
|
|
if fps is None:
|
|
|
|
fps = _bpy.context.scene.render.fps
|
|
|
|
|
|
|
|
if fps_base is None:
|
|
|
|
fps_base = _bpy.context.scene.render.fps_base
|
|
|
|
|
2019-06-19 10:49:37 -07:00
|
|
|
fps = fps / fps_base
|
|
|
|
|
2012-05-28 16:06:38 +00:00
|
|
|
from datetime import timedelta
|
|
|
|
|
|
|
|
if isinstance(time, timedelta):
|
|
|
|
time = time.total_seconds()
|
|
|
|
|
2019-06-19 10:49:37 -07:00
|
|
|
return time * fps
|
2012-05-28 16:06:38 +00:00
|
|
|
|
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
def preset_find(name, preset_path, *, display_name=False, ext=".py"):
|
2010-09-14 16:45:24 +00:00
|
|
|
if not name:
|
|
|
|
return None
|
2011-01-01 07:20:34 +00:00
|
|
|
|
2010-09-14 04:58:25 +00:00
|
|
|
for directory in preset_paths(preset_path):
|
2011-01-01 07:20:34 +00:00
|
|
|
|
2010-09-14 04:58:25 +00:00
|
|
|
if display_name:
|
|
|
|
filename = ""
|
|
|
|
for fn in _os.listdir(directory):
|
2021-02-03 17:32:31 -07:00
|
|
|
if fn.endswith(ext) and name == _bpy.path.display_name(fn, title_case=False):
|
2010-09-14 04:58:25 +00:00
|
|
|
filename = fn
|
|
|
|
break
|
|
|
|
else:
|
2012-01-10 16:20:01 +00:00
|
|
|
filename = name + ext
|
2010-09-14 04:58:25 +00:00
|
|
|
|
|
|
|
if filename:
|
|
|
|
filepath = _os.path.join(directory, filename)
|
|
|
|
if _os.path.exists(filepath):
|
2010-09-14 16:45:24 +00:00
|
|
|
return filepath
|
|
|
|
|
|
|
|
|
2018-11-12 14:53:08 +01:00
|
|
|
def keyconfig_init():
|
|
|
|
# Key configuration initialization and refresh, called from the Blender
|
|
|
|
# window manager on startup and refresh.
|
2019-01-04 21:40:16 +01:00
|
|
|
active_config = _preferences.keymap.active_keyconfig
|
2018-11-12 14:53:08 +01:00
|
|
|
|
|
|
|
# Load the default key configuration.
|
2021-02-03 16:02:04 -07:00
|
|
|
default_filepath = preset_find("Blender", "keyconfig")
|
2018-11-12 14:53:08 +01:00
|
|
|
keyconfig_set(default_filepath)
|
|
|
|
|
|
|
|
# Set the active key configuration if different
|
|
|
|
filepath = preset_find(active_config, "keyconfig")
|
|
|
|
|
|
|
|
if filepath and filepath != default_filepath:
|
|
|
|
keyconfig_set(filepath)
|
|
|
|
|
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
def keyconfig_set(filepath, *, report=None):
|
2010-09-14 16:45:24 +00:00
|
|
|
from os.path import basename, splitext
|
|
|
|
|
2012-03-31 00:59:17 +00:00
|
|
|
if _bpy.app.debug_python:
|
2011-05-20 00:21:38 +00:00
|
|
|
print("loading preset:", filepath)
|
|
|
|
|
2010-09-14 16:45:24 +00:00
|
|
|
keyconfigs = _bpy.context.window_manager.keyconfigs
|
|
|
|
|
|
|
|
try:
|
2013-06-11 15:11:55 +00:00
|
|
|
error_msg = ""
|
2018-11-18 11:49:03 +11:00
|
|
|
execfile(filepath)
|
2010-09-14 16:45:24 +00:00
|
|
|
except:
|
|
|
|
import traceback
|
2013-06-11 15:11:55 +00:00
|
|
|
error_msg = traceback.format_exc()
|
|
|
|
|
2019-02-14 11:11:53 +11:00
|
|
|
name = splitext(basename(filepath))[0]
|
|
|
|
kc_new = keyconfigs.get(name)
|
|
|
|
|
2013-06-11 15:11:55 +00:00
|
|
|
if error_msg:
|
|
|
|
if report is not None:
|
|
|
|
report({'ERROR'}, error_msg)
|
|
|
|
print(error_msg)
|
2019-02-14 11:11:53 +11:00
|
|
|
if kc_new is not None:
|
|
|
|
keyconfigs.remove(kc_new)
|
|
|
|
return False
|
2018-11-12 14:53:08 +01:00
|
|
|
|
|
|
|
# Get name, exception for default keymap to keep backwards compatibility.
|
2013-06-11 15:11:55 +00:00
|
|
|
if kc_new is None:
|
|
|
|
if report is not None:
|
|
|
|
report({'ERROR'}, "Failed to load keymap %r" % filepath)
|
|
|
|
return False
|
|
|
|
else:
|
|
|
|
keyconfigs.active = kc_new
|
|
|
|
return True
|
2010-09-14 16:45:24 +00:00
|
|
|
|
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
def user_resource(resource_type, *, path="", create=False):
|
2010-12-18 07:22:52 +00:00
|
|
|
"""
|
|
|
|
Return a user resource path (normally from the users home directory).
|
|
|
|
|
|
|
|
:arg type: Resource type in ['DATAFILES', 'CONFIG', 'SCRIPTS', 'AUTOSAVE'].
|
|
|
|
:type type: string
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
:arg path: Optional subdirectory.
|
|
|
|
:type path: string
|
2011-07-31 03:15:37 +00:00
|
|
|
:arg create: Treat the path as a directory and create
|
|
|
|
it if its not existing.
|
2010-12-18 07:22:52 +00:00
|
|
|
:type create: boolean
|
|
|
|
:return: a path.
|
|
|
|
:rtype: string
|
|
|
|
"""
|
|
|
|
|
PyAPI: use keyword only arguments
Use keyword only arguments for the following functions.
- addon_utils.module_bl_info 2nd arg `info_basis`.
- addon_utils.modules 1st `module_cache`, 2nd arg `refresh`.
- addon_utils.modules_refresh 1st arg `module_cache`.
- bl_app_template_utils.activate 1nd arg `template_id`.
- bl_app_template_utils.import_from_id 2nd arg `ignore_not_found`.
- bl_app_template_utils.import_from_path 2nd arg `ignore_not_found`.
- bl_keymap_utils.keymap_from_toolbar.generate 2nd & 3rd args `use_fallback_keys` & `use_reset`.
- bl_keymap_utils.platform_helpers.keyconfig_data_oskey_from_ctrl 2nd arg `filter_fn`.
- bl_ui_utils.bug_report_url.url_prefill_from_blender 1st arg `addon_info`.
- bmesh.types.BMFace.copy 1st & 2nd args `verts`, `edges`.
- bmesh.types.BMesh.calc_volume 1st arg `signed`.
- bmesh.types.BMesh.from_mesh 2nd..4th args `face_normals`, `use_shape_key`, `shape_key_index`.
- bmesh.types.BMesh.from_object 3rd & 4th args `cage`, `face_normals`.
- bmesh.types.BMesh.transform 2nd arg `filter`.
- bmesh.types.BMesh.update_edit_mesh 2nd & 3rd args `loop_triangles`, `destructive`.
- bmesh.types.{BMVertSeq,BMEdgeSeq,BMFaceSeq}.sort 1st & 2nd arg `key`, `reverse`.
- bmesh.utils.face_split 4th..6th args `coords`, `use_exist`, `example`.
- bpy.data.libraries.load 2nd..4th args `link`, `relative`, `assets_only`.
- bpy.data.user_map 1st..3rd args `subset`, `key_types, `value_types`.
- bpy.msgbus.subscribe_rna 5th arg `options`.
- bpy.path.abspath 2nd & 3rd args `start` & `library`.
- bpy.path.clean_name 2nd arg `replace`.
- bpy.path.ensure_ext 3rd arg `case_sensitive`.
- bpy.path.module_names 2nd arg `recursive`.
- bpy.path.relpath 2nd arg `start`.
- bpy.types.EditBone.transform 2nd & 3rd arg `scale`, `roll`.
- bpy.types.Operator.as_keywords 1st arg `ignore`.
- bpy.types.Struct.{keyframe_insert,keyframe_delete} 2nd..5th args `index`, `frame`, `group`, `options`.
- bpy.types.WindowManager.popup_menu 2nd & 3rd arg `title`, `icon`.
- bpy.types.WindowManager.popup_menu_pie 3rd & 4th arg `title`, `icon`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.app_template_paths 1st arg `subdir`.
- bpy.utils.blend_paths 1st..3rd args `absolute`, `packed`, `local`.
- bpy.utils.execfile 2nd arg `mod`.
- bpy.utils.keyconfig_set 2nd arg `report`.
- bpy.utils.load_scripts 1st & 2nd `reload_scripts` & `refresh_scripts`.
- bpy.utils.preset_find 3rd & 4th args `display_name`, `ext`.
- bpy.utils.resource_path 2nd & 3rd arg `major`, `minor`.
- bpy.utils.script_paths 1st..4th args `subdir`, `user_pref`, `check_all`, `use_user`.
- bpy.utils.smpte_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.smpte_from_seconds 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.system_resource 2nd arg `subdir`.
- bpy.utils.time_from_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.time_to_frame 2nd & 3rd args `fps`, `fps_base`.
- bpy.utils.units.to_string 4th..6th `precision`, `split_unit`, `compatible_unit`.
- bpy.utils.units.to_value 4th arg `str_ref_unit`.
- bpy.utils.user_resource 2nd & 3rd args `subdir`, `create`
- bpy_extras.view3d_utils.location_3d_to_region_2d 4th arg `default`.
- bpy_extras.view3d_utils.region_2d_to_origin_3d 4th arg `clamp`.
- gpu.offscreen.unbind 1st arg `restore`.
- gpu_extras.batch.batch_for_shader 4th arg `indices`.
- gpu_extras.batch.presets.draw_circle_2d 4th arg `segments`.
- gpu_extras.presets.draw_circle_2d 4th arg `segments`.
- imbuf.types.ImBuf.resize 2nd arg `resize`.
- imbuf.write 2nd arg `filepath`.
- mathutils.kdtree.KDTree.find 2nd arg `filter`.
- nodeitems_utils.NodeCategory 3rd & 4th arg `descriptions`, `items`.
- nodeitems_utils.NodeItem 2nd..4th args `label`, `settings`, `poll`.
- nodeitems_utils.NodeItemCustom 1st & 2nd arg `poll`, `draw`.
- rna_prop_ui.draw 5th arg `use_edit`.
- rna_prop_ui.rna_idprop_ui_get 2nd arg `create`.
- rna_prop_ui.rna_idprop_ui_prop_clear 3rd arg `remove`.
- rna_prop_ui.rna_idprop_ui_prop_get 3rd arg `create`.
- rna_xml.xml2rna 2nd arg `root_rna`.
- rna_xml.xml_file_write 4th arg `skip_typemap`.
2021-06-08 18:03:14 +10:00
|
|
|
target_path = _user_resource(resource_type, path=path)
|
2010-12-18 07:22:52 +00:00
|
|
|
|
|
|
|
if create:
|
|
|
|
# should always be true.
|
|
|
|
if target_path:
|
|
|
|
# create path if not existing.
|
|
|
|
if not _os.path.exists(target_path):
|
|
|
|
try:
|
|
|
|
_os.makedirs(target_path)
|
|
|
|
except:
|
|
|
|
import traceback
|
|
|
|
traceback.print_exc()
|
|
|
|
target_path = ""
|
|
|
|
elif not _os.path.isdir(target_path):
|
2010-12-19 07:05:29 +00:00
|
|
|
print("Path %r found but isn't a directory!" % target_path)
|
2010-12-18 07:22:52 +00:00
|
|
|
target_path = ""
|
|
|
|
|
|
|
|
return target_path
|
2011-02-10 23:48:22 +00:00
|
|
|
|
|
|
|
|
2017-09-05 00:22:31 +10:00
|
|
|
def register_classes_factory(classes):
|
|
|
|
"""
|
|
|
|
Utility function to create register and unregister functions
|
|
|
|
which simply registers and unregisters a sequence of classes.
|
|
|
|
"""
|
|
|
|
def register():
|
|
|
|
for cls in classes:
|
|
|
|
register_class(cls)
|
|
|
|
|
|
|
|
def unregister():
|
|
|
|
for cls in reversed(classes):
|
|
|
|
unregister_class(cls)
|
|
|
|
|
|
|
|
return register, unregister
|
|
|
|
|
|
|
|
|
2017-07-25 17:34:34 +10:00
|
|
|
def register_submodule_factory(module_name, submodule_names):
|
|
|
|
"""
|
|
|
|
Utility function to create register and unregister functions
|
|
|
|
which simply load submodules,
|
|
|
|
calling their register & unregister functions.
|
|
|
|
|
|
|
|
.. note::
|
|
|
|
|
|
|
|
Modules are registered in the order given,
|
|
|
|
unregistered in reverse order.
|
|
|
|
|
|
|
|
:arg module_name: The module name, typically ``__name__``.
|
|
|
|
:type module_name: string
|
|
|
|
:arg submodule_names: List of submodule names to load and unload.
|
|
|
|
:type submodule_names: list of strings
|
|
|
|
:return: register and unregister functions.
|
|
|
|
:rtype: tuple pair of functions
|
|
|
|
"""
|
|
|
|
|
|
|
|
module = None
|
|
|
|
submodules = []
|
|
|
|
|
|
|
|
def register():
|
|
|
|
nonlocal module
|
|
|
|
module = __import__(name=module_name, fromlist=submodule_names)
|
|
|
|
submodules[:] = [getattr(module, name) for name in submodule_names]
|
|
|
|
for mod in submodules:
|
|
|
|
mod.register()
|
|
|
|
|
|
|
|
def unregister():
|
|
|
|
from sys import modules
|
|
|
|
for mod in reversed(submodules):
|
|
|
|
mod.unregister()
|
|
|
|
name = mod.__name__
|
|
|
|
delattr(module, name.partition(".")[2])
|
|
|
|
del modules[name]
|
|
|
|
submodules.clear()
|
|
|
|
|
|
|
|
return register, unregister
|
|
|
|
|
|
|
|
|
2019-03-14 14:15:29 +11:00
|
|
|
# -----------------------------------------------------------------------------
|
|
|
|
# Tool Registration
|
|
|
|
|
|
|
|
|
|
|
|
def register_tool(tool_cls, *, after=None, separator=False, group=False):
|
|
|
|
"""
|
|
|
|
Register a tool in the toolbar.
|
|
|
|
|
|
|
|
:arg tool: A tool subclass.
|
|
|
|
:type tool: :class:`bpy.types.WorkSpaceTool` subclass.
|
|
|
|
:arg space_type: Space type identifier.
|
|
|
|
:type space_type: string
|
|
|
|
:arg after: Optional identifiers this tool will be added after.
|
|
|
|
:type after: collection of strings or None.
|
|
|
|
:arg separator: When true, add a separator before this tool.
|
|
|
|
:type separator: bool
|
|
|
|
:arg group: When true, add a new nested group of tools.
|
|
|
|
:type group: bool
|
|
|
|
"""
|
|
|
|
space_type = tool_cls.bl_space_type
|
|
|
|
context_mode = tool_cls.bl_context_mode
|
|
|
|
|
|
|
|
from bl_ui.space_toolsystem_common import (
|
|
|
|
ToolSelectPanelHelper,
|
|
|
|
ToolDef,
|
|
|
|
)
|
|
|
|
|
|
|
|
cls = ToolSelectPanelHelper._tool_class_from_space_type(space_type)
|
|
|
|
if cls is None:
|
2020-07-16 23:50:33 +10:00
|
|
|
raise Exception("Space type %r has no toolbar" % space_type)
|
2019-03-14 14:15:29 +11:00
|
|
|
tools = cls._tools[context_mode]
|
|
|
|
|
|
|
|
# First sanity check
|
|
|
|
from bpy.types import WorkSpaceTool
|
|
|
|
tools_id = {
|
|
|
|
item.idname for item in ToolSelectPanelHelper._tools_flatten(tools)
|
|
|
|
if item is not None
|
|
|
|
}
|
|
|
|
if not issubclass(tool_cls, WorkSpaceTool):
|
2020-07-16 23:50:33 +10:00
|
|
|
raise Exception("Expected WorkSpaceTool subclass, not %r" % type(tool_cls))
|
2019-03-14 14:15:29 +11:00
|
|
|
if tool_cls.bl_idname in tools_id:
|
2020-07-16 23:50:33 +10:00
|
|
|
raise Exception("Tool %r already exists!" % tool_cls.bl_idname)
|
2019-03-14 14:15:29 +11:00
|
|
|
del tools_id, WorkSpaceTool
|
|
|
|
|
|
|
|
# Convert the class into a ToolDef.
|
|
|
|
def tool_from_class(tool_cls):
|
|
|
|
# Convert class to tuple, store in the class for removal.
|
|
|
|
tool_def = ToolDef.from_dict({
|
|
|
|
"idname": tool_cls.bl_idname,
|
|
|
|
"label": tool_cls.bl_label,
|
|
|
|
"description": getattr(tool_cls, "bl_description", tool_cls.__doc__),
|
|
|
|
"icon": getattr(tool_cls, "bl_icon", None),
|
|
|
|
"cursor": getattr(tool_cls, "bl_cursor", None),
|
2021-09-21 17:55:43 +10:00
|
|
|
"options": getattr(tool_cls, "bl_options", None),
|
2019-03-14 14:15:29 +11:00
|
|
|
"widget": getattr(tool_cls, "bl_widget", None),
|
2021-08-26 16:02:31 +10:00
|
|
|
"widget_properties": getattr(tool_cls, "bl_widget_properties", None),
|
2019-03-14 14:15:29 +11:00
|
|
|
"keymap": getattr(tool_cls, "bl_keymap", None),
|
|
|
|
"data_block": getattr(tool_cls, "bl_data_block", None),
|
|
|
|
"operator": getattr(tool_cls, "bl_operator", None),
|
|
|
|
"draw_settings": getattr(tool_cls, "draw_settings", None),
|
|
|
|
"draw_cursor": getattr(tool_cls, "draw_cursor", None),
|
|
|
|
})
|
|
|
|
tool_cls._bl_tool = tool_def
|
|
|
|
|
|
|
|
keymap_data = tool_def.keymap
|
|
|
|
if keymap_data is not None:
|
|
|
|
if context_mode is None:
|
|
|
|
context_descr = "All"
|
|
|
|
else:
|
|
|
|
context_descr = context_mode.replace("_", " ").title()
|
|
|
|
from bpy import context
|
|
|
|
wm = context.window_manager
|
2020-03-27 17:15:12 +11:00
|
|
|
keyconfigs = wm.keyconfigs
|
|
|
|
kc_default = keyconfigs.default
|
|
|
|
# Note that Blender's default tools use the default key-config for both.
|
|
|
|
# We need to use the add-ons for 3rd party tools so reloading the key-map doesn't clear them.
|
|
|
|
kc = keyconfigs.addon
|
2019-03-14 14:15:29 +11:00
|
|
|
if callable(keymap_data[0]):
|
2020-03-27 17:15:12 +11:00
|
|
|
cls._km_action_simple(kc_default, kc, context_descr, tool_def.label, keymap_data)
|
2019-03-14 14:15:29 +11:00
|
|
|
return tool_def
|
|
|
|
|
|
|
|
tool_converted = tool_from_class(tool_cls)
|
|
|
|
|
|
|
|
if group:
|
|
|
|
# Create a new group
|
|
|
|
tool_converted = (tool_converted,)
|
|
|
|
|
|
|
|
tool_def_insert = (
|
|
|
|
(None, tool_converted) if separator else
|
|
|
|
(tool_converted,)
|
|
|
|
)
|
|
|
|
|
|
|
|
def skip_to_end_of_group(seq, i):
|
|
|
|
i_prev = i
|
|
|
|
while i < len(seq) and seq[i] is not None:
|
|
|
|
i_prev = i
|
|
|
|
i += 1
|
|
|
|
return i_prev
|
|
|
|
|
|
|
|
changed = False
|
|
|
|
if after is not None:
|
|
|
|
for i, item in enumerate(tools):
|
|
|
|
if item is None:
|
|
|
|
pass
|
|
|
|
elif isinstance(item, ToolDef):
|
|
|
|
if item.idname in after:
|
|
|
|
i = skip_to_end_of_group(item, i)
|
|
|
|
tools[i + 1:i + 1] = tool_def_insert
|
|
|
|
changed = True
|
|
|
|
break
|
|
|
|
elif isinstance(item, tuple):
|
|
|
|
for j, sub_item in enumerate(item, 1):
|
|
|
|
if isinstance(sub_item, ToolDef):
|
|
|
|
if sub_item.idname in after:
|
|
|
|
if group:
|
|
|
|
# Can't add a group within a group,
|
|
|
|
# add a new group after this group.
|
|
|
|
i = skip_to_end_of_group(tools, i)
|
|
|
|
tools[i + 1:i + 1] = tool_def_insert
|
|
|
|
else:
|
|
|
|
j = skip_to_end_of_group(item, j)
|
|
|
|
item = item[:j + 1] + tool_def_insert + item[j + 1:]
|
|
|
|
tools[i] = item
|
|
|
|
changed = True
|
|
|
|
break
|
|
|
|
if changed:
|
|
|
|
break
|
|
|
|
|
|
|
|
if not changed:
|
|
|
|
print("bpy.utils.register_tool: could not find 'after'", after)
|
|
|
|
if not changed:
|
|
|
|
tools.extend(tool_def_insert)
|
|
|
|
|
|
|
|
|
|
|
|
def unregister_tool(tool_cls):
|
|
|
|
space_type = tool_cls.bl_space_type
|
|
|
|
context_mode = tool_cls.bl_context_mode
|
|
|
|
|
|
|
|
from bl_ui.space_toolsystem_common import ToolSelectPanelHelper
|
|
|
|
cls = ToolSelectPanelHelper._tool_class_from_space_type(space_type)
|
|
|
|
if cls is None:
|
2020-07-16 23:50:33 +10:00
|
|
|
raise Exception("Space type %r has no toolbar" % space_type)
|
2019-03-14 14:15:29 +11:00
|
|
|
tools = cls._tools[context_mode]
|
|
|
|
|
|
|
|
tool_def = tool_cls._bl_tool
|
|
|
|
try:
|
|
|
|
i = tools.index(tool_def)
|
|
|
|
except ValueError:
|
|
|
|
i = -1
|
|
|
|
|
|
|
|
def tool_list_clean(tool_list):
|
|
|
|
# Trim separators.
|
|
|
|
while tool_list and tool_list[-1] is None:
|
|
|
|
del tool_list[-1]
|
|
|
|
while tool_list and tool_list[0] is None:
|
|
|
|
del tool_list[0]
|
|
|
|
# Remove duplicate separators.
|
|
|
|
for i in range(len(tool_list) - 1, -1, -1):
|
|
|
|
is_none = tool_list[i] is None
|
|
|
|
if is_none and prev_is_none:
|
|
|
|
del tool_list[i]
|
|
|
|
prev_is_none = is_none
|
|
|
|
|
|
|
|
changed = False
|
|
|
|
if i != -1:
|
|
|
|
del tools[i]
|
|
|
|
tool_list_clean(tools)
|
|
|
|
changed = True
|
|
|
|
|
|
|
|
if not changed:
|
|
|
|
for i, item in enumerate(tools):
|
|
|
|
if isinstance(item, tuple):
|
|
|
|
try:
|
|
|
|
j = item.index(tool_def)
|
|
|
|
except ValueError:
|
|
|
|
j = -1
|
|
|
|
|
|
|
|
if j != -1:
|
|
|
|
item_clean = list(item)
|
|
|
|
del item_clean[j]
|
|
|
|
tool_list_clean(item_clean)
|
|
|
|
if item_clean:
|
|
|
|
tools[i] = tuple(item_clean)
|
|
|
|
else:
|
|
|
|
del tools[i]
|
|
|
|
tool_list_clean(tools)
|
|
|
|
del item_clean
|
|
|
|
|
|
|
|
# tuple(sub_item for sub_item in items if sub_item is not tool_def)
|
|
|
|
changed = True
|
|
|
|
break
|
|
|
|
|
|
|
|
if not changed:
|
2020-07-16 23:50:33 +10:00
|
|
|
raise Exception("Unable to remove %r" % tool_cls)
|
2019-03-14 14:15:29 +11:00
|
|
|
del tool_cls._bl_tool
|
|
|
|
|
|
|
|
keymap_data = tool_def.keymap
|
|
|
|
if keymap_data is not None:
|
|
|
|
from bpy import context
|
|
|
|
wm = context.window_manager
|
2020-03-27 17:15:12 +11:00
|
|
|
keyconfigs = wm.keyconfigs
|
|
|
|
for kc in (keyconfigs.default, keyconfigs.addon):
|
|
|
|
km = kc.keymaps.get(keymap_data[0])
|
|
|
|
if km is None:
|
2020-07-16 23:50:33 +10:00
|
|
|
print("Warning keymap %r not found in %r!" % (keymap_data[0], kc.name))
|
2020-03-27 17:15:12 +11:00
|
|
|
else:
|
|
|
|
kc.keymaps.remove(km)
|
2019-03-14 14:15:29 +11:00
|
|
|
|
|
|
|
|
2012-08-25 14:07:51 +00:00
|
|
|
# -----------------------------------------------------------------------------
|
|
|
|
# Manual lookups, each function has to return a basepath and a sequence
|
|
|
|
# of...
|
|
|
|
|
|
|
|
# we start with the built-in default mapping
|
|
|
|
def _blender_default_map():
|
2023-02-09 11:07:49 +11:00
|
|
|
# NOTE(@ideasman42): Avoid importing this as there is no need to keep the lookup table in memory.
|
|
|
|
# As this runs when the user accesses the "Online Manual", the overhead loading the file is acceptable.
|
|
|
|
# In my tests it's under 1/100th of a second loading from a `pyc`.
|
|
|
|
ref_mod = execfile(_os.path.join(_script_base_dir, "modules", "rna_manual_reference.py"))
|
|
|
|
return (ref_mod.url_manual_prefix, ref_mod.url_manual_mapping)
|
2012-08-25 14:07:51 +00:00
|
|
|
|
2018-07-03 22:35:37 +02:00
|
|
|
|
2012-08-25 14:07:51 +00:00
|
|
|
# hooks for doc lookups
|
|
|
|
_manual_map = [_blender_default_map]
|
|
|
|
|
2012-09-26 21:19:51 +00:00
|
|
|
|
2012-08-25 14:07:51 +00:00
|
|
|
def register_manual_map(manual_hook):
|
|
|
|
_manual_map.append(manual_hook)
|
|
|
|
|
2012-09-26 21:19:51 +00:00
|
|
|
|
2012-08-25 14:07:51 +00:00
|
|
|
def unregister_manual_map(manual_hook):
|
|
|
|
_manual_map.remove(manual_hook)
|
|
|
|
|
2012-09-26 21:19:51 +00:00
|
|
|
|
2012-08-25 14:07:51 +00:00
|
|
|
def manual_map():
|
|
|
|
# reverse so default is called last
|
|
|
|
for cb in reversed(_manual_map):
|
|
|
|
try:
|
|
|
|
prefix, url_manual_mapping = cb()
|
|
|
|
except:
|
|
|
|
print("Error calling %r" % cb)
|
|
|
|
import traceback
|
|
|
|
traceback.print_exc()
|
|
|
|
continue
|
|
|
|
|
|
|
|
yield prefix, url_manual_mapping
|
2013-02-24 08:50:55 +00:00
|
|
|
|
|
|
|
|
2023-02-10 11:01:02 +11:00
|
|
|
# Languages which are supported by the user manual (commented when there is no translation).
|
|
|
|
_manual_language_codes = {
|
|
|
|
"ar_EG": "ar", # Arabic
|
|
|
|
# "bg_BG": "bg", # Bulgarian
|
|
|
|
# "ca_AD": "ca", # Catalan
|
|
|
|
# "cs_CZ": "cz", # Czech
|
|
|
|
"de_DE": "de", # German
|
|
|
|
# "el_GR": "el", # Greek
|
|
|
|
"es": "es", # Spanish
|
|
|
|
"fi_FI": "fi", # Finnish
|
|
|
|
"fr_FR": "fr", # French
|
|
|
|
"id_ID": "id", # Indonesian
|
|
|
|
"it_IT": "it", # Italian
|
|
|
|
"ja_JP": "ja", # Japanese
|
|
|
|
"ko_KR": "ko", # Korean
|
|
|
|
# "nb": "nb", # Norwegian
|
|
|
|
# "nl_NL": "nl", # Dutch
|
|
|
|
# "pl_PL": "pl", # Polish
|
|
|
|
"pt_PT": "pt", # Portuguese
|
|
|
|
# Portuguese - Brazil, for until we have a pt_BR version.
|
|
|
|
"pt_BR": "pt",
|
|
|
|
"ru_RU": "ru", # Russian
|
|
|
|
"sk_SK": "sk", # Slovak
|
|
|
|
# "sl": "sl", # Slovenian
|
|
|
|
"sr_RS": "sr", # Serbian
|
|
|
|
# "sv_SE": "sv", # Swedish
|
|
|
|
# "tr_TR": "th", # Thai
|
|
|
|
"uk_UA": "uk", # Ukrainian
|
|
|
|
"vi_VN": "vi", # Vietnamese
|
|
|
|
"zh_CN": "zh-hans", # Simplified Chinese
|
|
|
|
"zh_TW": "zh-hant", # Traditional Chinese
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
def manual_language_code(default="en"):
|
|
|
|
"""
|
|
|
|
:return:
|
|
|
|
The language code used for user manual URL component based on the current language user-preference,
|
|
|
|
falling back to the ``default`` when unavailable.
|
|
|
|
:rtype: str
|
|
|
|
"""
|
|
|
|
language = _bpy.context.preferences.view.language
|
|
|
|
if language == 'DEFAULT':
|
|
|
|
language = _os.getenv("LANG", "").split(".")[0]
|
|
|
|
return _manual_language_codes.get(language, default)
|
|
|
|
|
|
|
|
|
2013-02-24 08:50:55 +00:00
|
|
|
# Build an RNA path from struct/property/enum names.
|
|
|
|
def make_rna_paths(struct_name, prop_name, enum_name):
|
|
|
|
"""
|
|
|
|
Create RNA "paths" from given names.
|
|
|
|
|
|
|
|
:arg struct_name: Name of a RNA struct (like e.g. "Scene").
|
|
|
|
:type struct_name: string
|
|
|
|
:arg prop_name: Name of a RNA struct's property.
|
|
|
|
:type prop_name: string
|
|
|
|
:arg enum_name: Name of a RNA enum identifier.
|
|
|
|
:type enum_name: string
|
2013-04-07 01:38:03 +00:00
|
|
|
:return: A triple of three "RNA paths"
|
|
|
|
(most_complete_path, "struct.prop", "struct.prop:'enum'").
|
|
|
|
If no enum_name is given, the third element will always be void.
|
2013-02-24 08:50:55 +00:00
|
|
|
:rtype: tuple of strings
|
|
|
|
"""
|
|
|
|
src = src_rna = src_enum = ""
|
|
|
|
if struct_name:
|
|
|
|
if prop_name:
|
|
|
|
src = src_rna = ".".join((struct_name, prop_name))
|
|
|
|
if enum_name:
|
2013-10-16 04:08:20 +00:00
|
|
|
src = src_enum = "%s:'%s'" % (src_rna, enum_name)
|
2013-02-24 08:50:55 +00:00
|
|
|
else:
|
|
|
|
src = src_rna = struct_name
|
|
|
|
return src, src_rna, src_enum
|