[Bf-blender-cvs] [f4ba7667dc3] blender2.8: UI: support tool generators (no visible change)

Campbell Barton noreply at git.blender.org
Sun Apr 29 12:28:28 CEST 2018


Commit: f4ba7667dc34edc3fbd1118f8f0dbe818a8e7d43
Author: Campbell Barton
Date:   Sun Apr 29 12:26:00 2018 +0200
Branches: blender2.8
https://developer.blender.org/rBf4ba7667dc34edc3fbd1118f8f0dbe818a8e7d43

UI: support tool generators (no visible change)

This allows toolbar definitions to dynamically generate tools,
needed for generating a tool list from brushes for eg.

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

M	release/scripts/startup/bl_ui/space_toolsystem_common.py
M	release/scripts/startup/bl_ui/space_toolsystem_toolbar.py

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

diff --git a/release/scripts/startup/bl_ui/space_toolsystem_common.py b/release/scripts/startup/bl_ui/space_toolsystem_common.py
index 6bbf311b520..f3ff59718ce 100644
--- a/release/scripts/startup/bl_ui/space_toolsystem_common.py
+++ b/release/scripts/startup/bl_ui/space_toolsystem_common.py
@@ -58,6 +58,10 @@ def _keymap_fn_from_seq(keymap_data):
     return keymap_fn
 
 
+def _item_is_fn(item):
+    return (not (type(item) is type and issubclass(item, ToolDef)) and callable(item))
+
+
 class ToolDef:
     """
     Tool definition,
@@ -137,14 +141,23 @@ class ToolSelectPanelHelper:
 
     @staticmethod
     def _tools_flatten(tools):
+        """
+        Flattens, skips None and calls generators.
+        """
         for item in tools:
             if item is not None:
                 if type(item) is tuple:
                     for sub_item in item:
                         if sub_item is not None:
-                            yield sub_item
+                            if _item_is_fn(sub_item):
+                                yield from sub_item(context)
+                            else:
+                                yield sub_item
                 else:
-                    yield item
+                    if _item_is_fn(item):
+                        yield from item(context)
+                    else:
+                        yield item
 
     @classmethod
     def _tool_vars_from_def(cls, item, context_mode):
@@ -220,7 +233,8 @@ class ToolSelectPanelHelper:
                 if item_parent is None:
                     continue
                 for item in item_parent if (type(item_parent) is tuple) else (item_parent,):
-                    if item is None:
+                    # skip None or generator function
+                    if item is None or _item_is_fn(item):
                         continue
                     keymap_data = item.keymap
                     if keymap_data is not None:
@@ -341,68 +355,63 @@ class ToolSelectPanelHelper:
         # Start iteration
         ui_gen.send(None)
 
-        for tool_items in self.tools_from_context(context):
-            if tool_items:
-                for item in tool_items:
-                    if item is None:
-                        ui_gen.send(True)
-                        continue
-
-                    if type(item) is tuple:
-                        is_active = False
-                        i = 0
-                        for i, sub_item in enumerate(item):
-                            if sub_item is None:
-                                continue
-                            tool_def, icon_name = self._tool_vars_from_def(sub_item, context_mode)
-                            is_active = (tool_def == tool_def_active)
-                            if is_active:
-                                index = i
-                                break
-                        del i, sub_item
+        for item in self.tools_from_context(context):
+                if item is None:
+                    ui_gen.send(True)
+                    continue
 
+                if type(item) is tuple:
+                    is_active = False
+                    i = 0
+                    for i, sub_item in enumerate(item):
+                        if sub_item is None:
+                            continue
+                        tool_def, icon_name = self._tool_vars_from_def(sub_item, context_mode)
+                        is_active = (tool_def == tool_def_active)
                         if is_active:
-                            # not ideal, write this every time :S
-                            self._tool_group_active[item[0].text] = index
-                        else:
-                            index = self._tool_group_active.get(item[0].text, 0)
+                            index = i
+                            break
+                    del i, sub_item
 
-                        item = item[index]
-                        use_menu = True
+                    if is_active:
+                        # not ideal, write this every time :S
+                        self._tool_group_active[item[0].text] = index
                     else:
-                        index = -1
-                        use_menu = False
-
-                    tool_def, icon_name = self._tool_vars_from_def(item, context_mode)
-                    is_active = (tool_def == tool_def_active)
-                    icon_value = ToolSelectPanelHelper._icon_value_from_icon_handle(icon_name)
-
-                    sub = ui_gen.send(False)
-
-                    if use_menu:
-                        props = sub.operator_menu_hold(
-                            "wm.tool_set",
-                            text=item.text if show_text else "",
-                            depress=is_active,
-                            menu="WM_MT_toolsystem_submenu",
-                            icon_value=icon_value,
-                        )
-                    else:
-                        props = sub.operator(
-                            "wm.tool_set",
-                            text=item.text if show_text else "",
-                            depress=is_active,
-                            icon_value=icon_value,
-                        )
-                    props.keymap = tool_def[0] or ""
-                    props.manipulator_group = tool_def[1] or ""
-                    props.index = index
+                        index = self._tool_group_active.get(item[0].text, 0)
+
+                    item = item[index]
+                    use_menu = True
+                else:
+                    index = -1
+                    use_menu = False
+
+                tool_def, icon_name = self._tool_vars_from_def(item, context_mode)
+                is_active = (tool_def == tool_def_active)
+                icon_value = ToolSelectPanelHelper._icon_value_from_icon_handle(icon_name)
+
+                sub = ui_gen.send(False)
+
+                if use_menu:
+                    props = sub.operator_menu_hold(
+                        "wm.tool_set",
+                        text=item.text if show_text else "",
+                        depress=is_active,
+                        menu="WM_MT_toolsystem_submenu",
+                        icon_value=icon_value,
+                    )
+                else:
+                    props = sub.operator(
+                        "wm.tool_set",
+                        text=item.text if show_text else "",
+                        depress=is_active,
+                        icon_value=icon_value,
+                    )
+                props.keymap = tool_def[0] or ""
+                props.manipulator_group = tool_def[1] or ""
+                props.index = index
         # Signal to finish any remaining layout edits.
         ui_gen.send(None)
 
-    def tools_from_context(cls, context):
-        return (cls._tools[None], cls._tools.get(context.mode, ()))
-
     @staticmethod
     def _active_tool(context, with_icon=False):
         """
@@ -420,15 +429,14 @@ class ToolSelectPanelHelper:
             tool_def_active, index_active = ToolSelectPanelHelper._tool_vars_from_active_with_index(context)
 
             context_mode = context.mode
-            for tool_items in cls.tools_from_context(context):
-                for item in cls._tools_flatten(tool_items):
-                    tool_def, icon_name = cls._tool_vars_from_def(item, context_mode)
-                    if (tool_def == tool_def_active):
-                        if with_icon:
-                            icon_value = ToolSelectPanelHelper._icon_value_from_icon_handle(icon_name)
-                        else:
-                            icon_value = 0
-                        return (item, icon_value)
+            for item in cls._tools_flatten(cls.tools_from_context(context)):
+                tool_def, icon_name = cls._tool_vars_from_def(item, context_mode)
+                if (tool_def == tool_def_active):
+                    if with_icon:
+                        icon_value = ToolSelectPanelHelper._icon_value_from_icon_handle(icon_name)
+                    else:
+                        icon_value = 0
+                    return (item, icon_value)
         return None, 0
 
     @staticmethod
diff --git a/release/scripts/startup/bl_ui/space_toolsystem_toolbar.py b/release/scripts/startup/bl_ui/space_toolsystem_toolbar.py
index 029c1c7642f..1bcb9c1a592 100644
--- a/release/scripts/startup/bl_ui/space_toolsystem_toolbar.py
+++ b/release/scripts/startup/bl_ui/space_toolsystem_toolbar.py
@@ -414,7 +414,13 @@ class VIEW3D_PT_tools_active(ToolSelectPanelHelper, Panel):
 
     @classmethod
     def tools_from_context(cls, context):
-        return (cls._tools[None], cls._tools.get(context.mode, ()))
+        for tools in (cls._tools[None], cls._tools.get(context.mode, ())):
+            for item in tools:
+                if not (type(item) is type and issubclass(item, ToolDef)) and callable(item):
+                    yield from item(context)
+                else:
+                    yield item
+
 
     @classmethod
     def tools_all(cls):



More information about the Bf-blender-cvs mailing list