Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--release/scripts/startup/bl_ui/space_toolsystem_common.py15
-rw-r--r--release/scripts/startup/bl_ui/space_toolsystem_toolbar.py22
-rw-r--r--source/blender/blenkernel/intern/workspace.c5
-rw-r--r--source/blender/blenloader/intern/readfile.c1
-rw-r--r--source/blender/blenloader/intern/writefile.c5
-rw-r--r--source/blender/makesdna/DNA_workspace_types.h13
-rw-r--r--source/blender/makesrna/intern/rna_workspace_api.c24
-rw-r--r--source/blender/windowmanager/WM_api.h6
-rw-r--r--source/blender/windowmanager/intern/wm_event_system.c33
-rw-r--r--source/blender/windowmanager/intern/wm_toolsystem.c46
-rw-r--r--source/blender/windowmanager/wm_event_system.h1
11 files changed, 140 insertions, 31 deletions
diff --git a/release/scripts/startup/bl_ui/space_toolsystem_common.py b/release/scripts/startup/bl_ui/space_toolsystem_common.py
index 717beac1289..8a494369cf5 100644
--- a/release/scripts/startup/bl_ui/space_toolsystem_common.py
+++ b/release/scripts/startup/bl_ui/space_toolsystem_common.py
@@ -237,14 +237,11 @@ class ToolSelectPanelHelper:
"""
Return the active Python tool definition and icon name.
"""
-
workspace = context.workspace
cls = ToolSelectPanelHelper._tool_class_from_space_type(space_type)
if cls is not None:
- tool_active_text = getattr(
- ToolSelectPanelHelper._tool_active_from_context(context, space_type, mode),
- "name", None)
-
+ tool_active = ToolSelectPanelHelper._tool_active_from_context(context, space_type, mode)
+ tool_active_text = getattr(tool_active, "name", None)
for item in ToolSelectPanelHelper._tools_flatten(cls.tools_from_context(context, mode)):
if item is not None:
if item.text == tool_active_text:
@@ -252,8 +249,8 @@ class ToolSelectPanelHelper:
icon_value = ToolSelectPanelHelper._icon_value_from_icon_handle(item.icon)
else:
icon_value = 0
- return (item, icon_value)
- return None, 0
+ return (item, tool_active, icon_value)
+ return None, None, 0
@staticmethod
def _tool_get_by_name(context, space_type, text):
@@ -517,14 +514,14 @@ class ToolSelectPanelHelper:
workspace = context.workspace
space_type = workspace.tools_space_type
mode = workspace.tools_mode
- item, icon_value = ToolSelectPanelHelper._tool_get_active(context, space_type, mode, with_icon=True)
+ item, tool, icon_value = ToolSelectPanelHelper._tool_get_active(context, space_type, mode, with_icon=True)
if item is None:
return
# Note: we could show 'item.text' here but it makes the layout jitter when switcuing tools.
layout.label(" ", icon_value=icon_value)
draw_settings = item.draw_settings
if draw_settings is not None:
- draw_settings(context, layout)
+ draw_settings(context, layout, tool)
# The purpose of this menu is to be a generic popup to select between tools
diff --git a/release/scripts/startup/bl_ui/space_toolsystem_toolbar.py b/release/scripts/startup/bl_ui/space_toolsystem_toolbar.py
index 137ca779065..8bcd56ce561 100644
--- a/release/scripts/startup/bl_ui/space_toolsystem_toolbar.py
+++ b/release/scripts/startup/bl_ui/space_toolsystem_toolbar.py
@@ -293,9 +293,9 @@ class _defs_edit_mesh:
@ToolDef.from_fn
def rip_region():
- def draw_settings(context, layout):
+ def draw_settings(context, layout, tool):
wm = context.window_manager
- props = wm.operator_properties_last("mesh.rip_move")
+ props = tool.operator_properties("mesh.rip_move")
props_macro = props.MESH_OT_rip
layout.prop(props_macro, "use_fill")
@@ -393,9 +393,9 @@ class _defs_edit_mesh:
@ToolDef.from_fn
def inset():
- def draw_settings(context, layout):
+ def draw_settings(context, layout, tool):
wm = context.window_manager
- props = wm.operator_properties_last("mesh.inset")
+ props = tool.operator_properties("mesh.inset")
layout.prop(props, "use_outset")
layout.prop(props, "use_individual")
layout.prop(props, "use_even_offset")
@@ -507,9 +507,9 @@ class _defs_edit_mesh:
@ToolDef.from_fn
def shrink_fatten():
- def draw_settings(context, layout):
+ def draw_settings(context, layout, tool):
wm = context.window_manager
- props = wm.operator_properties_last("transform.shrink_fatten")
+ props = tool.operator_properties("transform.shrink_fatten")
layout.prop(props, "use_even_offset")
return dict(
@@ -537,9 +537,9 @@ class _defs_edit_mesh:
@ToolDef.from_fn
def knife():
- def draw_settings(context, layout):
+ def draw_settings(context, layout, tool):
wm = context.window_manager
- props = wm.operator_properties_last("mesh.knife_tool")
+ props = tool.operator_properties("mesh.knife_tool")
layout.prop(props, "use_occlude_geometry")
layout.prop(props, "only_selected")
@@ -573,7 +573,7 @@ class _defs_edit_curve:
@ToolDef.from_fn
def draw():
- def draw_settings(context, layout):
+ def draw_settings(context, layout, tool):
# Tool settings initialize operator options.
tool_settings = context.tool_settings
cps = tool_settings.curve_paint_settings
@@ -765,9 +765,9 @@ class _defs_weight_paint:
@ToolDef.from_fn
def gradient():
- def draw_settings(context, layout):
+ def draw_settings(context, layout, tool):
wm = context.window_manager
- props = wm.operator_properties_last("paint.weight_gradient")
+ props = tool.operator_properties("paint.weight_gradient")
layout.prop(props, "type")
return dict(
diff --git a/source/blender/blenkernel/intern/workspace.c b/source/blender/blenkernel/intern/workspace.c
index fd316cb9d82..7fc0d814089 100644
--- a/source/blender/blenkernel/intern/workspace.c
+++ b/source/blender/blenkernel/intern/workspace.c
@@ -34,6 +34,7 @@
#include "BLI_listbase.h"
#include "BKE_global.h"
+#include "BKE_idprop.h"
#include "BKE_library.h"
#include "BKE_main.h"
#include "BKE_scene.h"
@@ -176,6 +177,10 @@ void BKE_workspace_free(WorkSpace *workspace)
tref_next = tref->next;
if (tref->runtime) {
MEM_freeN(tref->runtime);
+ if (tref->properties) {
+ IDP_FreeProperty(tref->properties);
+ MEM_freeN(tref->properties);
+ }
}
}
BLI_freelistN(&workspace->tools);
diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c
index a8181f1e043..c92b27bdb1c 100644
--- a/source/blender/blenloader/intern/readfile.c
+++ b/source/blender/blenloader/intern/readfile.c
@@ -2941,6 +2941,7 @@ static void direct_link_workspace(FileData *fd, WorkSpace *workspace, const Main
for (bToolRef *tref = workspace->tools.first; tref; tref = tref->next) {
tref->runtime = NULL;
+ tref->properties = newdataadr(fd, tref->properties);
}
}
diff --git a/source/blender/blenloader/intern/writefile.c b/source/blender/blenloader/intern/writefile.c
index 8ea1205be38..a3cac39f609 100644
--- a/source/blender/blenloader/intern/writefile.c
+++ b/source/blender/blenloader/intern/writefile.c
@@ -3602,6 +3602,11 @@ static void write_workspace(WriteData *wd, WorkSpace *workspace)
writelist(wd, DATA, WorkSpaceDataRelation, &workspace->scene_viewlayer_relations);
writelist(wd, DATA, wmOwnerID, &workspace->owner_ids);
writelist(wd, DATA, bToolRef, &workspace->tools);
+ for (bToolRef *tref = workspace->tools.first; tref; tref = tref->next) {
+ if (tref->properties) {
+ IDP_WriteProperty(tref->properties, wd);
+ }
+ }
}
/* Keep it last of write_foodata functions. */
diff --git a/source/blender/makesdna/DNA_workspace_types.h b/source/blender/makesdna/DNA_workspace_types.h
index 24fa0e06d90..ca9186e16bf 100644
--- a/source/blender/makesdna/DNA_workspace_types.h
+++ b/source/blender/makesdna/DNA_workspace_types.h
@@ -56,11 +56,13 @@
#
#
typedef struct bToolRef_Runtime {
- /* One of these must be defined. */
int cursor;
+
+ /* One of these 3 must be defined. */
char keymap[64];
char manipulator_group[64];
char data_block[64];
+
/* index when a tool is a member of a group */
int index;
} bToolRef_Runtime;
@@ -82,6 +84,15 @@ typedef struct bToolRef {
*/
int mode;
+ /**
+ * Use for tool options, each group's name must match a tool name:
+ *
+ * {"Tool Name": {"SOME_OT_operator": {...}, ..}, ..}
+ *
+ * This is done since different tools may call the same operators with their own options.
+ */
+ IDProperty *properties;
+
/** Variables needed to operate the tool. */
bToolRef_Runtime *runtime;
} bToolRef;
diff --git a/source/blender/makesrna/intern/rna_workspace_api.c b/source/blender/makesrna/intern/rna_workspace_api.c
index 4c6949cc33d..e56d9a0bc33 100644
--- a/source/blender/makesrna/intern/rna_workspace_api.c
+++ b/source/blender/makesrna/intern/rna_workspace_api.c
@@ -64,6 +64,20 @@ static void rna_WorkspaceTool_setup(
WM_toolsystem_ref_set_from_runtime(C, (WorkSpace *)id, tref, &tref_rt, name);
}
+static PointerRNA rna_WorkspaceTool_operator_properties(
+ bToolRef *tref,
+ const char *idname)
+{
+ wmOperatorType *ot = WM_operatortype_find(idname, true);
+
+ if (ot != NULL) {
+ PointerRNA ptr;
+ WM_toolsystem_ref_properties_ensure(tref, ot, &ptr);
+ return ptr;
+ }
+ return PointerRNA_NULL;
+}
+
#else
void RNA_api_workspace(StructRNA *UNUSED(srna))
@@ -91,6 +105,16 @@ void RNA_api_workspace_tool(StructRNA *srna)
RNA_def_string(func, "manipulator_group", NULL, MAX_NAME, "Manipulator Group", "");
RNA_def_string(func, "data_block", NULL, MAX_NAME, "Data Block", "");
RNA_def_int(func, "index", 0, INT_MIN, INT_MAX, "Index", "", INT_MIN, INT_MAX);
+
+ /* Access tool operator options (optionally create). */
+ func = RNA_def_function(srna, "operator_properties", "rna_WorkspaceTool_operator_properties");
+ parm = RNA_def_string(func, "operator", NULL, 0, "", "");
+ RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
+ /* return */
+ parm = RNA_def_pointer(func, "result", "OperatorProperties", "", "");
+ RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_RNAPTR);
+ RNA_def_function_return(func, parm);
+
}
#endif
diff --git a/source/blender/windowmanager/WM_api.h b/source/blender/windowmanager/WM_api.h
index 050edb980e9..33222b2f1f1 100644
--- a/source/blender/windowmanager/WM_api.h
+++ b/source/blender/windowmanager/WM_api.h
@@ -646,6 +646,12 @@ bool WM_toolsystem_active_tool_is_brush(const struct bContext *C);
void WM_toolsystem_do_msg_notify_tag_refresh(
struct bContext *C, struct wmMsgSubscribeKey *msg_key, struct wmMsgSubscribeValue *msg_val);
+struct IDProperty *WM_toolsystem_ref_properties_ensure_idprops(struct bToolRef *tref);
+void WM_toolsystem_ref_properties_ensure(struct bToolRef *tref, struct wmOperatorType *ot, struct PointerRNA *ptr);
+
+void WM_toolsystem_ref_properties_init_for_keymap(
+ struct bToolRef *tref, struct PointerRNA *dst_ptr, struct PointerRNA *src_ptr, struct wmOperatorType *ot);
+
/* wm_tooltip.c */
typedef struct ARegion *(*wmTooltipInitFn)(struct bContext *, struct ARegion *, bool *);
diff --git a/source/blender/windowmanager/intern/wm_event_system.c b/source/blender/windowmanager/intern/wm_event_system.c
index df19f30e31e..f49f961f505 100644
--- a/source/blender/windowmanager/intern/wm_event_system.c
+++ b/source/blender/windowmanager/intern/wm_event_system.c
@@ -1235,7 +1235,8 @@ bool WM_operator_last_properties_store(wmOperator *UNUSED(op))
*/
static int wm_operator_invoke(
bContext *C, wmOperatorType *ot, wmEvent *event,
- PointerRNA *properties, ReportList *reports, const bool poll_only)
+ PointerRNA *properties, ReportList *reports,
+ const bool poll_only, bool use_last_properties)
{
int retval = OPERATOR_PASS_THROUGH;
@@ -1253,7 +1254,7 @@ static int wm_operator_invoke(
}
/* initialize setting from previous run */
- if (!is_nested_call) { /* not called by py script */
+ if (!is_nested_call && use_last_properties) { /* not called by py script */
WM_operator_last_properties_init(op);
}
@@ -1301,7 +1302,7 @@ static int wm_operator_invoke(
/* do nothing, wm_operator_exec() has been called somewhere */
}
else if (retval & OPERATOR_FINISHED) {
- const bool store = !is_nested_call;
+ const bool store = !is_nested_call && use_last_properties;
wm_operator_finished(C, op, false, store);
}
else if (retval & OPERATOR_RUNNING_MODAL) {
@@ -1464,7 +1465,7 @@ static int wm_operator_call_internal(
CTX_wm_region_set(C, ar1);
}
- retval = wm_operator_invoke(C, ot, event, properties, reports, poll_only);
+ retval = wm_operator_invoke(C, ot, event, properties, reports, poll_only, true);
/* set region back */
CTX_wm_region_set(C, ar);
@@ -1478,7 +1479,7 @@ static int wm_operator_call_internal(
ARegion *ar = CTX_wm_region(C);
CTX_wm_region_set(C, NULL);
- retval = wm_operator_invoke(C, ot, event, properties, reports, poll_only);
+ retval = wm_operator_invoke(C, ot, event, properties, reports, poll_only, true);
CTX_wm_region_set(C, ar);
return retval;
@@ -1492,7 +1493,7 @@ static int wm_operator_call_internal(
CTX_wm_region_set(C, NULL);
CTX_wm_area_set(C, NULL);
- retval = wm_operator_invoke(C, ot, event, properties, reports, poll_only);
+ retval = wm_operator_invoke(C, ot, event, properties, reports, poll_only, true);
CTX_wm_area_set(C, area);
CTX_wm_region_set(C, ar);
@@ -1500,7 +1501,7 @@ static int wm_operator_call_internal(
}
case WM_OP_EXEC_DEFAULT:
case WM_OP_INVOKE_DEFAULT:
- return wm_operator_invoke(C, ot, event, properties, reports, poll_only);
+ return wm_operator_invoke(C, ot, event, properties, reports, poll_only, true);
}
}
@@ -1975,9 +1976,19 @@ static int wm_handler_operator_call(bContext *C, ListBase *handlers, wmEventHand
else {
wmOperatorType *ot = WM_operatortype_find(event->keymap_idname, 0);
- if (ot) {
- if (wm_operator_check_locked_interface(C, ot)) {
- retval = wm_operator_invoke(C, ot, event, properties, NULL, false);
+ if (ot && wm_operator_check_locked_interface(C, ot)) {
+ bool use_last_properties = true;
+ PointerRNA tool_properties = {0};
+ if (handler->keymap_tool) {
+ WM_toolsystem_ref_properties_init_for_keymap(handler->keymap_tool, &tool_properties, properties, ot);
+ properties = &tool_properties;
+ use_last_properties = false;
+ }
+
+ retval = wm_operator_invoke(C, ot, event, properties, NULL, false, use_last_properties);
+
+ if (handler->keymap_tool) {
+ WM_operator_properties_free(&tool_properties);
}
}
}
@@ -2887,6 +2898,8 @@ void wm_event_do_handlers(bContext *C)
C, tref_rt->keymap, sa->spacetype, RGN_TYPE_WINDOW);
if (km != NULL) {
sneaky_handler.keymap = km;
+ sneaky_handler.keymap_tool = sa->runtime.tool;
+
/* Handle widgets first. */
wmEventHandler *handler_last = ar->handlers.last;
while (handler_last && handler_last->manipulator_map == NULL) {
diff --git a/source/blender/windowmanager/intern/wm_toolsystem.c b/source/blender/windowmanager/intern/wm_toolsystem.c
index c616d143b69..3d9c6d88d2c 100644
--- a/source/blender/windowmanager/intern/wm_toolsystem.c
+++ b/source/blender/windowmanager/intern/wm_toolsystem.c
@@ -45,6 +45,7 @@
#include "BKE_library.h"
#include "BKE_main.h"
#include "BKE_paint.h"
+#include "BKE_idprop.h"
#include "BKE_workspace.h"
#include "RNA_access.h"
@@ -527,3 +528,48 @@ void WM_toolsystem_do_msg_notify_tag_refresh(
};
WM_toolsystem_refresh(C, workspace, &tkey);
}
+
+IDProperty *WM_toolsystem_ref_properties_ensure_idprops(bToolRef *tref)
+{
+ if (tref->properties == NULL) {
+ IDPropertyTemplate val = {0};
+ tref->properties = IDP_New(IDP_GROUP, &val, "wmOperatorProperties");
+ }
+ return tref->properties;
+}
+
+void WM_toolsystem_ref_properties_ensure(bToolRef *tref, wmOperatorType *ot, PointerRNA *ptr)
+{
+ IDProperty *group = WM_toolsystem_ref_properties_ensure_idprops(tref);
+ IDProperty *prop = IDP_GetPropertyFromGroup(group, ot->idname);
+ if (prop == NULL) {
+ IDPropertyTemplate val = {0};
+ prop = IDP_New(IDP_GROUP, &val, "wmOperatorProperties");
+ STRNCPY(prop->name, ot->idname);
+ IDP_ReplaceInGroup_ex(group, prop, NULL);
+ }
+ else {
+ BLI_assert(prop->type == IDP_GROUP);
+ }
+
+ RNA_pointer_create(NULL, ot->srna, prop, ptr);
+}
+
+void WM_toolsystem_ref_properties_init_for_keymap(
+ bToolRef *tref, PointerRNA *dst_ptr, PointerRNA *src_ptr, wmOperatorType *ot)
+{
+ *dst_ptr = *src_ptr;
+ if (dst_ptr->data) {
+ dst_ptr->data = IDP_CopyProperty(dst_ptr->data);
+ }
+ else {
+ IDPropertyTemplate val = {0};
+ dst_ptr->data = IDP_New(IDP_GROUP, &val, "wmOpItemProp");
+ }
+ if (tref->properties != NULL) {
+ IDProperty *prop = IDP_GetPropertyFromGroup(tref->properties, ot->idname);
+ if (prop) {
+ IDP_MergeGroup(dst_ptr->data, prop, true);
+ }
+ }
+}
diff --git a/source/blender/windowmanager/wm_event_system.h b/source/blender/windowmanager/wm_event_system.h
index 452fe377665..7b18ed54c85 100644
--- a/source/blender/windowmanager/wm_event_system.h
+++ b/source/blender/windowmanager/wm_event_system.h
@@ -54,6 +54,7 @@ typedef struct wmEventHandler {
/* Run after the keymap item runs. */
void (*keymap_callback)(wmKeyMap *keymap, wmKeyMapItem *kmi, void *user_data);
void *keymap_callback_user_data;
+ struct bToolRef *keymap_tool;
/* modal operator handler */
wmOperator *op; /* for derived/modal handlers */