diff options
author | Lukas Toenne <lukas.toenne@googlemail.com> | 2012-03-07 16:30:29 +0400 |
---|---|---|
committer | Lukas Toenne <lukas.toenne@googlemail.com> | 2012-03-07 16:30:29 +0400 |
commit | 43711d856891c46c1dc898554f40534d9b5f529f (patch) | |
tree | 3d37b62a648480c972611c9f4c1c91a171985100 | |
parent | e6c2f05efad729911d4bfd52b0c1b44c506e272c (diff) |
Simplified the ntreeUpdate function by getting rid of the dependency list and limiting resorting to cases where it is actually necessary (when nodes get added/removed or links change).
Node updates should generally be local by design, i.e. changes should not depend on any of the other nodes in the same tree. The original purpose of the dependency sort was to allow some experimental nodes to update their socket types based on upstream connected nodes, but these have been removed long ago. If such features need to be implemented they should instead use the tree-wide update callback, which is called after all the local node updates are done.
Removing the extra allocation and recursive function calls from most updates will ensure this function stays as fast as possible and can be called during node space context updates (snode_set_context), which are done very frequently (redraw).
-rw-r--r-- | source/blender/blenkernel/intern/node.c | 62 |
1 files changed, 37 insertions, 25 deletions
diff --git a/source/blender/blenkernel/intern/node.c b/source/blender/blenkernel/intern/node.c index 9d61a12d237..8b9955dd378 100644 --- a/source/blender/blenkernel/intern/node.c +++ b/source/blender/blenkernel/intern/node.c @@ -1447,6 +1447,24 @@ void ntreeGetDependencyList(struct bNodeTree *ntree, struct bNode ***deplist, in } } +/* only updates node->level for detecting cycles links */ +static void ntree_update_node_level(bNodeTree *ntree) +{ + bNode *node; + + /* first clear tag */ + for(node= ntree->nodes.first; node; node= node->next) { + node->done= 0; + } + + /* recursive check */ + for(node= ntree->nodes.first; node; node= node->next) { + if(node->done==0) { + node->level= node_get_deplist_recurs(node, NULL); + } + } +} + static void ntree_update_link_pointers(bNodeTree *ntree) { bNode *node; @@ -1524,39 +1542,33 @@ void ntreeUpdateTree(bNodeTree *ntree) { bNodeTreeType *ntreetype= ntreeGetType(ntree->type); bNode *node; - bNode **deplist; - int totnodes, n; - ntree_update_link_pointers(ntree); + /* set the bNodeSocket->link pointers */ + if (ntree->update & NTREE_UPDATE_LINKS) + ntree_update_link_pointers(ntree); - /* also updates the node level! */ - ntreeGetDependencyList(ntree, &deplist, &totnodes); + /* update the node level from link dependencies */ + if (ntree->update & (NTREE_UPDATE_LINKS|NTREE_UPDATE_NODES)) + ntree_update_node_level(ntree); - if (deplist) { - /* update individual nodes */ - for (n=0; n < totnodes; ++n) { - node = deplist[n]; - - /* node tree update tags override individual node update flags */ - if ((node->update & NODE_UPDATE) || (ntree->update & NTREE_UPDATE)) { - if (ntreetype->update_node) - ntreetype->update_node(ntree, node); - else if (node->typeinfo->updatefunc) - node->typeinfo->updatefunc(ntree, node); - } - /* clear update flag */ - node->update = 0; + /* update individual nodes */ + for (node=ntree->nodes.first; node; node=node->next) { + /* node tree update tags override individual node update flags */ + if ((node->update & NODE_UPDATE) || (ntree->update & NTREE_UPDATE)) { + if (ntreetype->update_node) + ntreetype->update_node(ntree, node); + else if (node->typeinfo->updatefunc) + node->typeinfo->updatefunc(ntree, node); } - - MEM_freeN(deplist); + /* clear update flag */ + node->update = 0; } - /* general tree updates */ - if (ntree->update & (NTREE_UPDATE_LINKS|NTREE_UPDATE_NODES)) { + /* check link validity */ + if (ntree->update & (NTREE_UPDATE_LINKS|NTREE_UPDATE_NODES)) ntree_validate_links(ntree); - } - /* update tree */ + /* generic tree update callback */ if (ntreetype->update) ntreetype->update(ntree); else { |