diff options
21 files changed, 224 insertions, 79 deletions
diff --git a/source/blender/blenkernel/BKE_node.h b/source/blender/blenkernel/BKE_node.h index 30c76dc894c..d6c4ad037e2 100644 --- a/source/blender/blenkernel/BKE_node.h +++ b/source/blender/blenkernel/BKE_node.h @@ -289,10 +289,22 @@ typedef struct bNodeType { void (*freefunc_api)(struct PointerRNA *ptr); void (*copyfunc_api)(struct PointerRNA *ptr, const struct bNode *src_node); - /* can this node type be added to a node tree */ - bool (*poll)(struct bNodeType *ntype, struct bNodeTree *nodetree); - /* can this node be added to a node tree */ - bool (*poll_instance)(struct bNode *node, struct bNodeTree *nodetree); + /** + * Can this node type be added to a node tree? + * \param r_disabled_hint: Optional hint to display in the UI when the poll fails. + * The callback can set this to a static string without having to + * null-check it (or without setting it to null if it's not used). + * The caller must pass a valid `const char **` and null-initialize it + * when it's not just a dummy, that is, if it actually wants to access + * the returned disabled-hint (null-check needed!). + */ + bool (*poll)(struct bNodeType *ntype, struct bNodeTree *nodetree, const char **r_disabled_hint); + /** Can this node be added to a node tree? + * \param r_disabled_hint: See `poll()`. + */ + bool (*poll_instance)(struct bNode *node, + struct bNodeTree *nodetree, + const char **r_disabled_hint); /* optional handling of link insertion */ void (*insert_link)(struct bNodeTree *ntree, struct bNode *node, struct bNodeLink *link); @@ -804,7 +816,9 @@ void BKE_node_preview_set_pixel( void nodeLabel(struct bNodeTree *ntree, struct bNode *node, char *label, int maxlen); const char *nodeSocketLabel(const struct bNodeSocket *sock); -int nodeGroupPoll(struct bNodeTree *nodetree, struct bNodeTree *grouptree); +bool nodeGroupPoll(struct bNodeTree *nodetree, + struct bNodeTree *grouptree, + const char **r_disabled_hint); /* Init a new node type struct with default values and callbacks */ void node_type_base(struct bNodeType *ntype, int type, const char *name, short nclass, short flag); diff --git a/source/blender/blenkernel/intern/node.cc b/source/blender/blenkernel/intern/node.cc index 52f6c4f93ad..02195e0d60f 100644 --- a/source/blender/blenkernel/intern/node.cc +++ b/source/blender/blenkernel/intern/node.cc @@ -2007,7 +2007,8 @@ bNode *nodeAddStaticNode(const struct bContext *C, bNodeTree *ntree, int type) /* do an extra poll here, because some int types are used * for multiple node types, this helps find the desired type */ - if (ntype->type == type && (!ntype->poll || ntype->poll(ntype, ntree))) { + const char *disabled_hint; + if (ntype->type == type && (!ntype->poll || ntype->poll(ntype, ntree, &disabled_hint))) { idname = ntype->idname; break; } @@ -4407,15 +4408,17 @@ static void node_type_base_defaults(bNodeType *ntype) } /* allow this node for any tree type */ -static bool node_poll_default(bNodeType *UNUSED(ntype), bNodeTree *UNUSED(ntree)) +static bool node_poll_default(bNodeType *UNUSED(ntype), + bNodeTree *UNUSED(ntree), + const char **UNUSED(disabled_hint)) { return true; } /* use the basic poll function */ -static bool node_poll_instance_default(bNode *node, bNodeTree *ntree) +static bool node_poll_instance_default(bNode *node, bNodeTree *ntree, const char **disabled_hint) { - return node->typeinfo->poll(node->typeinfo, ntree); + return node->typeinfo->poll(node->typeinfo, ntree, disabled_hint); } /* NOLINTNEXTLINE: readability-function-size */ @@ -4634,7 +4637,9 @@ void node_type_internal_links(bNodeType *ntype, /* callbacks for undefined types */ -static bool node_undefined_poll(bNodeType *UNUSED(ntype), bNodeTree *UNUSED(nodetree)) +static bool node_undefined_poll(bNodeType *UNUSED(ntype), + bNodeTree *UNUSED(nodetree), + const char **UNUSED(r_disabled_hint)) { /* this type can not be added deliberately, it's just a placeholder */ return false; diff --git a/source/blender/editors/space_node/node_add.c b/source/blender/editors/space_node/node_add.c index 82a315366dc..a28d467df2e 100644 --- a/source/blender/editors/space_node/node_add.c +++ b/source/blender/editors/space_node/node_add.c @@ -339,7 +339,25 @@ static bNodeTree *node_add_group_get_and_poll_group_node_tree(Main *bmain, if (!node_group) { return NULL; } - if ((node_group->type != ntree->type) || !nodeGroupPoll(ntree, node_group)) { + + const char *disabled_hint = NULL; + if ((node_group->type != ntree->type) || !nodeGroupPoll(ntree, node_group, &disabled_hint)) { + if (disabled_hint) { + BKE_reportf(op->reports, + RPT_ERROR, + "Can not add node group '%s' to '%s':\n %s", + node_group->id.name + 2, + ntree->id.name + 2, + disabled_hint); + } + else { + BKE_reportf(op->reports, + RPT_ERROR, + "Can not add node group '%s' to '%s'", + node_group->id.name + 2, + ntree->id.name + 2); + } + return NULL; } diff --git a/source/blender/editors/space_node/node_edit.c b/source/blender/editors/space_node/node_edit.c index 518f5639c93..1cbd0fd607c 100644 --- a/source/blender/editors/space_node/node_edit.c +++ b/source/blender/editors/space_node/node_edit.c @@ -2241,13 +2241,25 @@ static int node_clipboard_paste_exec(bContext *C, wmOperator *op) /* make sure all clipboard nodes would be valid in the target tree */ bool all_nodes_valid = true; LISTBASE_FOREACH (bNode *, node, clipboard_nodes_lb) { - if (!node->typeinfo->poll_instance || !node->typeinfo->poll_instance(node, ntree)) { + const char *disabled_hint = NULL; + if (!node->typeinfo->poll_instance || + !node->typeinfo->poll_instance(node, ntree, &disabled_hint)) { all_nodes_valid = false; - BKE_reportf(op->reports, - RPT_ERROR, - "Cannot add node %s into node tree %s", - node->name, - ntree->id.name + 2); + if (disabled_hint) { + BKE_reportf(op->reports, + RPT_ERROR, + "Cannot add node %s into node tree %s:\n %s", + node->name, + ntree->id.name + 2, + disabled_hint); + } + else { + BKE_reportf(op->reports, + RPT_ERROR, + "Cannot add node %s into node tree %s", + node->name, + ntree->id.name + 2); + } } } if (!all_nodes_valid) { diff --git a/source/blender/editors/space_node/node_group.c b/source/blender/editors/space_node/node_group.c index e1de4bfc21e..335e2f93ff3 100644 --- a/source/blender/editors/space_node/node_group.c +++ b/source/blender/editors/space_node/node_group.c @@ -679,8 +679,19 @@ static bool node_group_make_test_selected(bNodeTree *ntree, /* check poll functions for selected nodes */ LISTBASE_FOREACH (bNode *, node, &ntree->nodes) { if (node_group_make_use_node(node, gnode)) { - if (node->typeinfo->poll_instance && !node->typeinfo->poll_instance(node, ngroup)) { - BKE_reportf(reports, RPT_WARNING, "Can not add node '%s' in a group", node->name); + const char *disabled_hint = NULL; + if (node->typeinfo->poll_instance && + !node->typeinfo->poll_instance(node, ngroup, &disabled_hint)) { + if (disabled_hint) { + BKE_reportf(reports, + RPT_WARNING, + "Can not add node '%s' in a group:\n %s", + node->name, + disabled_hint); + } + else { + BKE_reportf(reports, RPT_WARNING, "Can not add node '%s' in a group", node->name); + } ok = false; break; } diff --git a/source/blender/editors/space_node/node_templates.c b/source/blender/editors/space_node/node_templates.c index 3873985d93a..54145f62895 100644 --- a/source/blender/editors/space_node/node_templates.c +++ b/source/blender/editors/space_node/node_templates.c @@ -330,7 +330,9 @@ static void ui_node_link_items(NodeLinkArg *arg, int i; for (ngroup = arg->bmain->nodetrees.first; ngroup; ngroup = ngroup->id.next) { - if ((ngroup->type != arg->ntree->type) || !nodeGroupPoll(arg->ntree, ngroup)) { + const char *disabled_hint; + if ((ngroup->type != arg->ntree->type) || + !nodeGroupPoll(arg->ntree, ngroup, &disabled_hint)) { continue; } @@ -343,7 +345,9 @@ static void ui_node_link_items(NodeLinkArg *arg, i = 0; for (ngroup = arg->bmain->nodetrees.first; ngroup; ngroup = ngroup->id.next) { - if ((ngroup->type != arg->ntree->type) || !nodeGroupPoll(arg->ntree, ngroup)) { + const char *disabled_hint; + if ((ngroup->type != arg->ntree->type) || + !nodeGroupPoll(arg->ntree, ngroup, &disabled_hint)) { continue; } @@ -481,7 +485,8 @@ static void ui_node_menu_column(NodeLinkArg *arg, int nclass, const char *cname) BLI_array_declare(sorted_ntypes); NODE_TYPES_BEGIN (ntype) { - if (!(ntype->poll && ntype->poll(ntype, ntree))) { + const char *disabled_hint; + if (!(ntype->poll && ntype->poll(ntype, ntree, &disabled_hint))) { continue; } diff --git a/source/blender/makesrna/intern/rna_nodetree.c b/source/blender/makesrna/intern/rna_nodetree.c index b79381ac26f..1016d31f11b 100644 --- a/source/blender/makesrna/intern/rna_nodetree.c +++ b/source/blender/makesrna/intern/rna_nodetree.c @@ -1085,13 +1085,25 @@ static bNode *rna_NodeTree_node_new(bNodeTree *ntree, return NULL; } - if (ntype->poll && !ntype->poll(ntype, ntree)) { - BKE_reportf(reports, - RPT_ERROR, - "Cannot add node of type %s to node tree '%s'", - type, - ntree->id.name + 2); - return NULL; + const char *disabled_hint = NULL; + if (ntype->poll && !ntype->poll(ntype, ntree, &disabled_hint)) { + if (disabled_hint) { + BKE_reportf(reports, + RPT_ERROR, + "Cannot add node of type %s to node tree '%s'\n %s", + type, + ntree->id.name + 2, + disabled_hint); + return NULL; + } + else { + BKE_reportf(reports, + RPT_ERROR, + "Cannot add node of type %s to node tree '%s'", + type, + ntree->id.name + 2); + return NULL; + } } node = nodeAddNode(C, ntree, type); @@ -1531,7 +1543,7 @@ char *rna_Node_ImageUser_path(PointerRNA *ptr) return NULL; } -static bool rna_Node_poll(bNodeType *ntype, bNodeTree *ntree) +static bool rna_Node_poll(bNodeType *ntype, bNodeTree *ntree, const char **UNUSED(r_disabled_hint)) { extern FunctionRNA rna_Node_poll_func; @@ -1556,7 +1568,9 @@ static bool rna_Node_poll(bNodeType *ntype, bNodeTree *ntree) return visible; } -static bool rna_Node_poll_instance(bNode *node, bNodeTree *ntree) +static bool rna_Node_poll_instance(bNode *node, + bNodeTree *ntree, + const char **UNUSED(disabled_info)) { extern FunctionRNA rna_Node_poll_instance_func; @@ -1581,10 +1595,12 @@ static bool rna_Node_poll_instance(bNode *node, bNodeTree *ntree) return visible; } -static bool rna_Node_poll_instance_default(bNode *node, bNodeTree *ntree) +static bool rna_Node_poll_instance_default(bNode *node, + bNodeTree *ntree, + const char **disabled_info) { /* use the basic poll function */ - return rna_Node_poll(node->typeinfo, ntree); + return rna_Node_poll(node->typeinfo, ntree, disabled_info); } static void rna_Node_update_reg(bNodeTree *ntree, bNode *node) @@ -3214,18 +3230,20 @@ static PointerRNA rna_NodeInternal_output_template(StructRNA *srna, int index) static bool rna_NodeInternal_poll(StructRNA *srna, bNodeTree *ntree) { bNodeType *ntype = RNA_struct_blender_type_get(srna); - return ntype && (!ntype->poll || ntype->poll(ntype, ntree)); + const char *disabled_hint; + return ntype && (!ntype->poll || ntype->poll(ntype, ntree, &disabled_hint)); } static bool rna_NodeInternal_poll_instance(bNode *node, bNodeTree *ntree) { bNodeType *ntype = node->typeinfo; + const char *disabled_hint; if (ntype->poll_instance) { - return ntype->poll_instance(node, ntree); + return ntype->poll_instance(node, ntree, &disabled_hint); } else { /* fall back to basic poll function */ - return !ntype->poll || ntype->poll(ntype, ntree); + return !ntype->poll || ntype->poll(ntype, ntree, &disabled_hint); } } @@ -3408,7 +3426,8 @@ static void rna_NodeGroup_node_tree_set(PointerRNA *ptr, bNode *node = ptr->data; bNodeTree *ngroup = value.data; - if (nodeGroupPoll(ntree, ngroup)) { + const char *disabled_hint = NULL; + if (nodeGroupPoll(ntree, ngroup, &disabled_hint)) { if (node->id) { id_us_min(node->id); } @@ -3430,7 +3449,8 @@ static bool rna_NodeGroup_node_tree_poll(PointerRNA *ptr, const PointerRNA value return false; } - return nodeGroupPoll(ntree, ngroup); + const char *disabled_hint = NULL; + return nodeGroupPoll(ntree, ngroup, &disabled_hint); } static StructRNA *rna_NodeGroup_interface_typef(PointerRNA *ptr) diff --git a/source/blender/nodes/composite/node_composite_util.c b/source/blender/nodes/composite/node_composite_util.c index b6cbffea413..6cc17d8c272 100644 --- a/source/blender/nodes/composite/node_composite_util.c +++ b/source/blender/nodes/composite/node_composite_util.c @@ -23,9 +23,15 @@ #include "node_composite_util.h" -bool cmp_node_poll_default(bNodeType *UNUSED(ntype), bNodeTree *ntree) +bool cmp_node_poll_default(bNodeType *UNUSED(ntype), + bNodeTree *ntree, + const char **r_disabled_hint) { - return STREQ(ntree->idname, "CompositorNodeTree"); + if (!STREQ(ntree->idname, "CompositorNodeTree")) { + *r_disabled_hint = "Not a compositor node tree"; + return false; + } + return true; } void cmp_node_update_default(bNodeTree *UNUSED(ntree), bNode *node) diff --git a/source/blender/nodes/composite/node_composite_util.h b/source/blender/nodes/composite/node_composite_util.h index 800c55df4d6..4fcccbb79f0 100644 --- a/source/blender/nodes/composite/node_composite_util.h +++ b/source/blender/nodes/composite/node_composite_util.h @@ -54,7 +54,9 @@ extern "C" { #define CMP_SCALE_MAX 12000 -bool cmp_node_poll_default(struct bNodeType *ntype, struct bNodeTree *ntree); +bool cmp_node_poll_default(struct bNodeType *ntype, + struct bNodeTree *ntree, + const char **r_disabled_info); void cmp_node_update_default(struct bNodeTree *ntree, struct bNode *node); void cmp_node_type_base( struct bNodeType *ntype, int type, const char *name, short nclass, short flag); diff --git a/source/blender/nodes/composite/nodes/node_composite_cryptomatte.cc b/source/blender/nodes/composite/nodes/node_composite_cryptomatte.cc index c5135482ec2..d9b36924516 100644 --- a/source/blender/nodes/composite/nodes/node_composite_cryptomatte.cc +++ b/source/blender/nodes/composite/nodes/node_composite_cryptomatte.cc @@ -263,7 +263,9 @@ static void node_copy_cryptomatte(bNodeTree *UNUSED(dest_ntree), dest_node->storage = dest_nc; } -static bool node_poll_cryptomatte(bNodeType *UNUSED(ntype), bNodeTree *ntree) +static bool node_poll_cryptomatte(bNodeType *UNUSED(ntype), + bNodeTree *ntree, + const char **r_disabled_hint) { if (STREQ(ntree->idname, "CompositorNodeTree")) { Scene *scene; @@ -276,8 +278,13 @@ static bool node_poll_cryptomatte(bNodeType *UNUSED(ntype), bNodeTree *ntree) } } + if (scene == nullptr) { + *r_disabled_hint = + "The node tree must be the compositing node tree of any scene in the file"; + } return scene != nullptr; } + *r_disabled_hint = "Not a compositor node tree"; return false; } diff --git a/source/blender/nodes/composite/nodes/node_composite_image.c b/source/blender/nodes/composite/nodes/node_composite_image.c index 53ea02ff8a7..243300b0a44 100644 --- a/source/blender/nodes/composite/nodes/node_composite_image.c +++ b/source/blender/nodes/composite/nodes/node_composite_image.c @@ -526,24 +526,32 @@ static void node_composit_init_rlayers(const bContext *C, PointerRNA *ptr) } } -static bool node_composit_poll_rlayers(bNodeType *UNUSED(ntype), bNodeTree *ntree) +static bool node_composit_poll_rlayers(bNodeType *UNUSED(ntype), + bNodeTree *ntree, + const char **r_disabled_hint) { - if (STREQ(ntree->idname, "CompositorNodeTree")) { - Scene *scene; + if (!STREQ(ntree->idname, "CompositorNodeTree")) { + *r_disabled_hint = "Not a compositor node tree"; + return false; + } - /* XXX ugly: check if ntree is a local scene node tree. - * Render layers node can only be used in local scene->nodetree, - * since it directly links to the scene. - */ - for (scene = G.main->scenes.first; scene; scene = scene->id.next) { - if (scene->nodetree == ntree) { - break; - } + Scene *scene; + + /* XXX ugly: check if ntree is a local scene node tree. + * Render layers node can only be used in local scene->nodetree, + * since it directly links to the scene. + */ + for (scene = G.main->scenes.first; scene; scene = scene->id.next) { + if (scene->nodetree == ntree) { + break; } + } - return (scene != NULL); + if (scene == NULL) { + *r_disabled_hint = "The node tree must be the compositing node tree of any scene in the file"; + return false; } - return false; + return true; } static void node_composit_free_rlayers(bNode *node) diff --git a/source/blender/nodes/function/node_function_util.cc b/source/blender/nodes/function/node_function_util.cc index 827572d1069..8ff8b416310 100644 --- a/source/blender/nodes/function/node_function_util.cc +++ b/source/blender/nodes/function/node_function_util.cc @@ -17,10 +17,16 @@ #include "node_function_util.hh" #include "node_util.h" -bool fn_node_poll_default(bNodeType *UNUSED(ntype), bNodeTree *ntree) +static bool fn_node_poll_default(bNodeType *UNUSED(ntype), + bNodeTree *ntree, + const char **r_disabled_hint) { /* Function nodes are only supported in simulation node trees so far. */ - return STREQ(ntree->idname, "GeometryNodeTree"); + if (!STREQ(ntree->idname, "GeometryNodeTree")) { + *r_disabled_hint = "Not a geometry node tree"; + return false; + } + return true; } void fn_node_type_base(bNodeType *ntype, int type, const char *name, short nclass, short flag) diff --git a/source/blender/nodes/function/node_function_util.hh b/source/blender/nodes/function/node_function_util.hh index d57d1383019..9fbd6712827 100644 --- a/source/blender/nodes/function/node_function_util.hh +++ b/source/blender/nodes/function/node_function_util.hh @@ -38,4 +38,3 @@ void fn_node_type_base( struct bNodeType *ntype, int type, const char *name, short nclass, short flag); -bool fn_node_poll_default(struct bNodeType *ntype, struct bNodeTree *ntree); diff --git a/source/blender/nodes/geometry/node_geometry_util.cc b/source/blender/nodes/geometry/node_geometry_util.cc index 0f725ecf211..93cada2982b 100644 --- a/source/blender/nodes/geometry/node_geometry_util.cc +++ b/source/blender/nodes/geometry/node_geometry_util.cc @@ -56,9 +56,15 @@ void update_attribute_input_socket_availabilities(bNode &node, } // namespace blender::nodes -bool geo_node_poll_default(bNodeType *UNUSED(ntype), bNodeTree *ntree) +bool geo_node_poll_default(bNodeType *UNUSED(ntype), + bNodeTree *ntree, + const char **r_disabled_hint) { - return STREQ(ntree->idname, "GeometryNodeTree"); + if (!STREQ(ntree->idname, "GeometryNodeTree")) { + *r_disabled_hint = "Not a geometry node tree"; + return false; + } + return true; } void geo_node_type_base(bNodeType *ntype, int type, const char *name, short nclass, short flag) diff --git a/source/blender/nodes/geometry/node_geometry_util.hh b/source/blender/nodes/geometry/node_geometry_util.hh index ad4f4331b6c..81092798ca1 100644 --- a/source/blender/nodes/geometry/node_geometry_util.hh +++ b/source/blender/nodes/geometry/node_geometry_util.hh @@ -36,7 +36,9 @@ void geo_node_type_base( struct bNodeType *ntype, int type, const char *name, short nclass, short flag); -bool geo_node_poll_default(struct bNodeType *ntype, struct bNodeTree *ntree); +bool geo_node_poll_default(struct bNodeType *ntype, + struct bNodeTree *ntree, + const char **r_disabled_hint); namespace blender::nodes { void update_attribute_input_socket_availabilities(bNode &node, diff --git a/source/blender/nodes/intern/node_common.c b/source/blender/nodes/intern/node_common.c index 0b1ab85c059..7fc9f664df0 100644 --- a/source/blender/nodes/intern/node_common.c +++ b/source/blender/nodes/intern/node_common.c @@ -79,12 +79,12 @@ void node_group_label(bNodeTree *UNUSED(ntree), bNode *node, char *label, int ma BLI_strncpy(label, (node->id) ? node->id->name + 2 : IFACE_("Missing Data-Block"), maxlen); } -bool node_group_poll_instance(bNode *node, bNodeTree *nodetree) +bool node_group_poll_instance(bNode *node, bNodeTree *nodetree, const char **disabled_hint) { - if (node->typeinfo->poll(node->typeinfo, nodetree)) { + if (node->typeinfo->poll(node->typeinfo, nodetree, disabled_hint)) { bNodeTree *grouptree = (bNodeTree *)node->id; if (grouptree) { - return nodeGroupPoll(nodetree, grouptree); + return nodeGroupPoll(nodetree, grouptree, disabled_hint); } return true; /* without a linked node tree, group node is always ok */ @@ -93,25 +93,27 @@ bool node_group_poll_instance(bNode *node, bNodeTree *nodetree) return false; } -int nodeGroupPoll(bNodeTree *nodetree, bNodeTree *grouptree) +bool nodeGroupPoll(bNodeTree *nodetree, bNodeTree *grouptree, const char **r_disabled_hint) { bNode *node; - int valid = 1; + bool valid = true; /* unspecified node group, generally allowed * (if anything, should be avoided on operator level) */ if (grouptree == NULL) { - return 1; + return true; } if (nodetree == grouptree) { - return 0; + *r_disabled_hint = "Nesting a node group inside of itself is not allowed"; + return false; } for (node = grouptree->nodes.first; node; node = node->next) { - if (node->typeinfo->poll_instance && !node->typeinfo->poll_instance(node, nodetree)) { - valid = 0; + if (node->typeinfo->poll_instance && + !node->typeinfo->poll_instance(node, nodetree, r_disabled_hint)) { + valid = false; break; } } diff --git a/source/blender/nodes/intern/node_common.h b/source/blender/nodes/intern/node_common.h index 7aad6782640..cdb7b6897b9 100644 --- a/source/blender/nodes/intern/node_common.h +++ b/source/blender/nodes/intern/node_common.h @@ -32,7 +32,9 @@ extern "C" { struct bNodeTree; void node_group_label(struct bNodeTree *ntree, struct bNode *node, char *label, int maxlen); -bool node_group_poll_instance(struct bNode *node, struct bNodeTree *nodetree); +bool node_group_poll_instance(struct bNode *node, + struct bNodeTree *nodetree, + const char **r_disabled_hint); void ntree_update_reroute_nodes(struct bNodeTree *ntree); diff --git a/source/blender/nodes/shader/node_shader_util.c b/source/blender/nodes/shader/node_shader_util.c index 1a2405e021f..04c32574a65 100644 --- a/source/blender/nodes/shader/node_shader_util.c +++ b/source/blender/nodes/shader/node_shader_util.c @@ -27,14 +27,24 @@ #include "node_exec.h" -bool sh_node_poll_default(bNodeType *UNUSED(ntype), bNodeTree *ntree) +bool sh_node_poll_default(bNodeType *UNUSED(ntype), bNodeTree *ntree, const char **r_disabled_hint) { - return STREQ(ntree->idname, "ShaderNodeTree"); + if (!STREQ(ntree->idname, "ShaderNodeTree")) { + *r_disabled_hint = "Not a shader node tree"; + return false; + } + return true; } -static bool sh_fn_poll_default(bNodeType *UNUSED(ntype), bNodeTree *ntree) +static bool sh_fn_poll_default(bNodeType *UNUSED(ntype), + bNodeTree *ntree, + const char **r_disabled_hint) { - return STREQ(ntree->idname, "ShaderNodeTree") || STREQ(ntree->idname, "GeometryNodeTree"); + if (!STREQ(ntree->idname, "ShaderNodeTree") && !STREQ(ntree->idname, "GeometryNodeTree")) { + *r_disabled_hint = "Not a shader or geometry node tree"; + return false; + } + return true; } void sh_node_type_base( diff --git a/source/blender/nodes/shader/node_shader_util.h b/source/blender/nodes/shader/node_shader_util.h index 91454c3c982..857a9914354 100644 --- a/source/blender/nodes/shader/node_shader_util.h +++ b/source/blender/nodes/shader/node_shader_util.h @@ -80,7 +80,9 @@ extern "C" { #endif -bool sh_node_poll_default(struct bNodeType *ntype, struct bNodeTree *ntree); +bool sh_node_poll_default(struct bNodeType *ntype, + struct bNodeTree *ntree, + const char **r_disabled_hint); void sh_node_type_base( struct bNodeType *ntype, int type, const char *name, short nclass, short flag); void sh_fn_node_type_base( diff --git a/source/blender/nodes/texture/node_texture_util.c b/source/blender/nodes/texture/node_texture_util.c index 2091a8bf10e..570b10d6e89 100644 --- a/source/blender/nodes/texture/node_texture_util.c +++ b/source/blender/nodes/texture/node_texture_util.c @@ -39,9 +39,15 @@ #include "node_texture_util.h" -bool tex_node_poll_default(bNodeType *UNUSED(ntype), bNodeTree *ntree) +bool tex_node_poll_default(bNodeType *UNUSED(ntype), + bNodeTree *ntree, + const char **r_disabled_hint) { - return STREQ(ntree->idname, "TextureNodeTree"); + if (!STREQ(ntree->idname, "TextureNodeTree")) { + *r_disabled_hint = "Not a texture node tree"; + return false; + } + return true; } void tex_node_type_base( diff --git a/source/blender/nodes/texture/node_texture_util.h b/source/blender/nodes/texture/node_texture_util.h index 74f27ef3974..8f63a1ad07d 100644 --- a/source/blender/nodes/texture/node_texture_util.h +++ b/source/blender/nodes/texture/node_texture_util.h @@ -106,7 +106,9 @@ typedef struct TexDelegate { int type; } TexDelegate; -bool tex_node_poll_default(struct bNodeType *ntype, struct bNodeTree *ntree); +bool tex_node_poll_default(struct bNodeType *ntype, + struct bNodeTree *ntree, + const char **r_disabled_hint); void tex_node_type_base( struct bNodeType *ntype, int type, const char *name, short nclass, short flag); |