Changeset View
Changeset View
Standalone View
Standalone View
release/scripts/modules/bpy/utils/module_loader.py
- This file was added.
| import bpy | |||||
| import inspect | |||||
| import importlib | |||||
| from bpy import types as bpy_types | |||||
| REGISTERABLE_CLASSES = ( | |||||
| bpy_types.Header, | |||||
| bpy_types.Menu, | |||||
| bpy_types.Operator, | |||||
| bpy_types.Macro, | |||||
| bpy_types.Panel, | |||||
| bpy_types.PropertyGroup, | |||||
| bpy.types.RenderEngine | |||||
| ) | |||||
| class ModuleLoader: | |||||
| def __init__(self, main_module): | |||||
| self.loaded_modules = [] | |||||
| self.main_module = main_module | |||||
| def import_modules(self, modules, package, reload = False): | |||||
| for module in modules: | |||||
| #print(("reloading " if reload else "loading ") + module) | |||||
| # import_module doesn't reload if already loaded, but we need a | |||||
| # reference to the module to reload. | |||||
| mod = importlib.import_module('.' + module, package) | |||||
| self.add_module(mod) | |||||
| if reload: | |||||
| importlib.reload(mod) | |||||
| def add_module(self, module): | |||||
| self.loaded_modules.append(module) | |||||
| def register_classes(self): | |||||
| for module in self._all_modules(): | |||||
| self._register_module_classes(module) | |||||
| def unregister_classes(self): | |||||
| for module in reversed(self._all_modules()): | |||||
| self._unregister_module_classes(module) | |||||
| def _all_modules(self): | |||||
| return [self.main_module] + self.loaded_modules | |||||
| # iterate all registerable classes in the given module. | |||||
| # sorts classes by the order that they were defined to handle | |||||
| # dependencies between classes. | |||||
| def _registerable_module_classes(self, module): | |||||
| classes = [] | |||||
| for name, obj in inspect.getmembers(module, inspect.isclass): | |||||
| for cls in REGISTERABLE_CLASSES: | |||||
| if issubclass(obj, cls) and obj != cls: | |||||
| #print(f"registerable class: {name}, class: {obj}") | |||||
| source, start_line = inspect.getsourcelines(obj) | |||||
| classes.append([obj, start_line]) | |||||
| def _line_order(value): | |||||
| return value[1] | |||||
| classes.sort(key = _line_order) | |||||
| for obj, start_line in classes: | |||||
| yield obj | |||||
| def _register_module_classes(self, module): | |||||
| #print(f"processing module {module}") | |||||
| for obj in self._registerable_module_classes(module): | |||||
| #print(f"registering {obj}") | |||||
| bpy.utils.register_class(obj) | |||||
| def _unregister_module_classes(self, module): | |||||
| for obj in reversed(list(self._registerable_module_classes(module))): | |||||
| #print(f"unregistering {obj}") | |||||
| bpy.utils.unregister_class(obj) | |||||