Fix T63892: Tools cannot be registered into some contexts (e.g.

PAINT_TEXTURE)

This fails because some tool contexts define their tools with functions
[see the following list for context that fail]:

- PARTICLE (_defs_particle.generate_from_brushes)
- SCULPT (_defs_sculpt.generate_from_brushes)
- PAINT_TEXTURE (_defs_texture_paint.generate_from_brushes)
- PAINT_VERTEX (_defs_vertex_paint.generate_from_brushes)
- PAINT_WEIGHT (_defs_weight_paint.generate_from_brushes)
- PAINT_GPENCIL (_defs_gpencil_paint.generate_from_brushes)
- SCULPT_GPENCIL (_defs_gpencil_sculpt.generate_from_brushes)
- WEIGHT_GPENCIL (_defs_gpencil_weight.generate_from_brushes)

ToolSelectPanelHelper._tools_flatten() is usually called with
cls.tools_from_context(context) [that already yields from the function].
But when registering a tool, _tools_flatten() will still give back this
function, not a ToolDef - and we cannot get a bl_idname from that.
Now check for this and yield None in that case.

Also share logic across all tool_flatten functions:
- _tools_flatten
- _tools_flatten_with_tool_index
- _tools_flatten_with_keymap

Maniphest Tasks: T63892

Differential Revision: https://developer.blender.org/D6763
This commit is contained in:
Philipp Oeser 2020-02-06 14:07:53 +01:00 committed by Nathan Letwory
parent 54f2d9dbe4
commit f9e51662bd
No known key found for this signature in database
GPG Key ID: 2C99F9D5FC4EFA4C
Notes: blender-bot 2023-02-14 19:16:35 +01:00
Referenced by issue blender/blender-addons#63892, Tools cannot be registered into some contexts (e.g. PAINT_TEXTURE).
1 changed files with 41 additions and 31 deletions

View File

@ -216,29 +216,52 @@ class ToolSelectPanelHelper:
else:
return 0
# tool flattening
#
# usually 'tools' is already expanded into ToolDef
# but when registering a tool, this can still be a function
# (_tools_flatten is usually called with cls.tools_from_context(context)
# [that already yields from the function])
# so if item is still a function (e.g._defs_XXX.generate_from_brushes)
# seems like we cannot expand here (have no context yet)
# if we yield None here, this will risk running into duplicate tool bl_idname [in register_tool()]
# but still better than erroring out
@staticmethod
def _tools_flatten(tools):
for item in tools:
if type(item) is tuple:
yield from item
else:
# May be None.
yield item
for item_parent in tools:
if item_parent is None:
yield None
for item in item_parent if (type(item_parent) is tuple) else (item_parent,):
if item is None or _item_is_fn(item):
yield None
else:
yield item
@staticmethod
def _tools_flatten_with_tool_index(tools):
for item in tools:
if type(item) is tuple:
i = 0
for sub_item in item:
if sub_item is None:
yield None, -1
else:
yield sub_item, i
i += 1
else:
# May be None.
yield item, -1
for item_parent in tools:
if item_parent is None:
yield None, -1
i = 0
for item in item_parent if (type(item_parent) is tuple) else (item_parent,):
if item is None or _item_is_fn(item):
yield None, -1
else:
yield item, i
i += 1
# Special internal function, gives use items that contain keymaps.
@staticmethod
def _tools_flatten_with_keymap(tools):
for item_parent in tools:
if item_parent is None:
continue
for item in item_parent if (type(item_parent) is tuple) else (item_parent,):
# skip None or generator function
if item is None or _item_is_fn(item):
continue
if item.keymap is not None:
yield item
@classmethod
def _tool_get_active(cls, context, space_type, mode, with_icon=False):
@ -405,19 +428,6 @@ class ToolSelectPanelHelper:
keymap_fn[0](km)
keymap_fn[0] = km.name
# Special internal function, gives use items that contain keymaps.
@staticmethod
def _tools_flatten_with_keymap(tools):
for item_parent in tools:
if item_parent is None:
continue
for item in item_parent if (type(item_parent) is tuple) else (item_parent,):
# skip None or generator function
if item is None or _item_is_fn(item):
continue
if item.keymap is not None:
yield item
@classmethod
def register(cls):
wm = bpy.context.window_manager