Automatically hide unused (=unlinked) node sockets in collapsed ("hidden") nodes. This is to make nodes with many sockets cleaner and simpler, which is the purpose of collapsing nodes in the first place.

The hiding code uses the SOCK_IN_USE flags already present. These were only temporarily set by the shader node code for determining needed texture coordinate types. Now they are used persistently and updated along with the sock->link pointers.
This commit is contained in:
Lukas Toenne
2011-12-19 12:04:05 +00:00
parent a9f0266448
commit 26b3dfa30e
5 changed files with 78 additions and 42 deletions

View File

@@ -305,8 +305,6 @@ void ntreeSwitchID(struct bNodeTree *ntree, struct ID *sce_from, struct ID *sc
void ntreeMakeLocal(struct bNodeTree *ntree);
int ntreeHasType(struct bNodeTree *ntree, int type);
void ntreeSocketUseFlags(struct bNodeTree *ntree);
void ntreeUpdateTree(struct bNodeTree *ntree);
/* XXX Currently each tree update call does call to ntreeVerifyNodes too.
* Some day this should be replaced by a decent depsgraph automatism!

View File

@@ -1325,32 +1325,6 @@ void nodeSetActive(bNodeTree *ntree, bNode *node)
node->flag |= NODE_ACTIVE_TEXTURE;
}
/* use flags are not persistent yet, groups might need different tagging, so we do it each time
when we need to get this info */
void ntreeSocketUseFlags(bNodeTree *ntree)
{
bNode *node;
bNodeSocket *sock;
bNodeLink *link;
/* clear flags */
for(node= ntree->nodes.first; node; node= node->next) {
for(sock= node->inputs.first; sock; sock= sock->next)
sock->flag &= ~SOCK_IN_USE;
for(sock= node->outputs.first; sock; sock= sock->next)
sock->flag &= ~SOCK_IN_USE;
}
/* tag all thats in use */
for(link= ntree->links.first; link; link= link->next) {
if(link->fromsock) // FIXME, see below
link->fromsock->flag |= SOCK_IN_USE;
if(link->tosock) // FIXME This can be NULL, when dragging a new link in the UI, should probably copy the node tree for preview render - campbell
link->tosock->flag |= SOCK_IN_USE;
}
}
/* ************** dependency stuff *********** */
/* node is guaranteed to be not checked before */
@@ -1425,16 +1399,27 @@ static void ntree_update_link_pointers(bNodeTree *ntree)
/* first clear data */
for(node= ntree->nodes.first; node; node= node->next) {
for(sock= node->inputs.first; sock; sock= sock->next)
for(sock= node->inputs.first; sock; sock= sock->next) {
sock->link= NULL;
sock->flag &= ~SOCK_IN_USE;
}
/* clear socket links */
for(sock= ntree->outputs.first; sock; sock= sock->next)
for(sock= node->outputs.first; sock; sock= sock->next) {
sock->flag &= ~SOCK_IN_USE;
}
}
for(sock= ntree->inputs.first; sock; sock= sock->next) {
sock->flag &= ~SOCK_IN_USE;
}
for(sock= ntree->outputs.first; sock; sock= sock->next) {
sock->link= NULL;
sock->flag &= ~SOCK_IN_USE;
}
for(link= ntree->links.first; link; link= link->next) {
if (link->tosock)
link->tosock->link= link;
link->fromsock->flag |= SOCK_IN_USE;
link->tosock->flag |= SOCK_IN_USE;
}
}

View File

@@ -7438,6 +7438,30 @@ void do_versions_image_settings_2_60(Scene *sce)
}
/* socket use flags were only temporary before */
static void do_versions_nodetree_socket_use_flags_2_62(bNodeTree *ntree)
{
bNode *node;
bNodeSocket *sock;
bNodeLink *link;
for (node=ntree->nodes.first; node; node=node->next) {
for (sock=node->inputs.first; sock; sock=sock->next)
sock->flag &= ~SOCK_IN_USE;
for (sock=node->outputs.first; sock; sock=sock->next)
sock->flag &= ~SOCK_IN_USE;
}
for (sock=ntree->inputs.first; sock; sock=sock->next)
sock->flag &= ~SOCK_IN_USE;
for (sock=ntree->outputs.first; sock; sock=sock->next)
sock->flag &= ~SOCK_IN_USE;
for (link=ntree->links.first; link; link=link->next) {
link->fromsock->flag |= SOCK_IN_USE;
link->tosock->flag |= SOCK_IN_USE;
}
}
static void do_versions(FileData *fd, Library *lib, Main *main)
{
/* WATCH IT!!!: pointers from libdata have not been converted */
@@ -12667,7 +12691,38 @@ static void do_versions(FileData *fd, Library *lib, Main *main)
/* put compatibility code here until next subversion bump */
{
/* nothing! */
{
/* update use flags for node sockets (was only temporary before) */
Scene *sce;
Material *mat;
Tex *tex;
Lamp *lamp;
World *world;
bNodeTree *ntree;
for (sce=main->scene.first; sce; sce=sce->id.next)
if (sce->nodetree)
do_versions_nodetree_socket_use_flags_2_62(sce->nodetree);
for (mat=main->mat.first; mat; mat=mat->id.next)
if (mat->nodetree)
do_versions_nodetree_socket_use_flags_2_62(mat->nodetree);
for (tex=main->tex.first; tex; tex=tex->id.next)
if (tex->nodetree)
do_versions_nodetree_socket_use_flags_2_62(tex->nodetree);
for (lamp=main->lamp.first; lamp; lamp=lamp->id.next)
if (lamp->nodetree)
do_versions_nodetree_socket_use_flags_2_62(lamp->nodetree);
for (world=main->world.first; world; world=world->id.next)
if (world->nodetree)
do_versions_nodetree_socket_use_flags_2_62(world->nodetree);
for (ntree=main->nodetree.first; ntree; ntree=ntree->id.next)
do_versions_nodetree_socket_use_flags_2_62(ntree);
}
}
/* WATCH IT!!!: pointers from libdata have not been converted yet here! */

View File

@@ -351,10 +351,10 @@ static void node_update_hidden(bNode *node)
/* calculate minimal radius */
for(nsock= node->inputs.first; nsock; nsock= nsock->next)
if(!(nsock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL)))
if(!(nsock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL)) && (nsock->flag & SOCK_IN_USE))
totin++;
for(nsock= node->outputs.first; nsock; nsock= nsock->next)
if(!(nsock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL)))
if(!(nsock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL)) && (nsock->flag & SOCK_IN_USE))
totout++;
tot= MAX2(totin, totout);
@@ -371,7 +371,7 @@ static void node_update_hidden(bNode *node)
rad=drad= (float)M_PI/(1.0f + (float)totout);
for(nsock= node->outputs.first; nsock; nsock= nsock->next) {
if(!(nsock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL))) {
if(!(nsock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL)) && (nsock->flag & SOCK_IN_USE)) {
nsock->locx= node->totr.xmax - hiddenrad + (float)sin(rad)*hiddenrad;
nsock->locy= node->totr.ymin + hiddenrad + (float)cos(rad)*hiddenrad;
rad+= drad;
@@ -382,7 +382,7 @@ static void node_update_hidden(bNode *node)
rad=drad= - (float)M_PI/(1.0f + (float)totin);
for(nsock= node->inputs.first; nsock; nsock= nsock->next) {
if(!(nsock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL))) {
if(!(nsock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL)) && (nsock->flag & SOCK_IN_USE)) {
nsock->locx= node->totr.xmin + hiddenrad + (float)sin(rad)*hiddenrad;
nsock->locy= node->totr.ymin + hiddenrad + (float)cos(rad)*hiddenrad;
rad+= drad;
@@ -854,12 +854,12 @@ static void node_draw_hidden(const bContext *C, ARegion *ar, SpaceNode *snode, b
/* sockets */
for(sock= node->inputs.first; sock; sock= sock->next) {
if(!(sock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL)))
if(!(sock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL)) && (sock->flag & SOCK_IN_USE))
node_socket_circle_draw(snode->nodetree, sock, socket_size);
}
for(sock= node->outputs.first; sock; sock= sock->next) {
if(!(sock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL)))
if(!(sock->flag & (SOCK_HIDDEN|SOCK_UNAVAIL)) && (sock->flag & SOCK_IN_USE))
node_socket_circle_draw(snode->nodetree, sock, socket_size);
}

View File

@@ -134,8 +134,6 @@ void ntreeShaderGetTexcoMode(bNodeTree *ntree, int r_mode, short *texco, int *mo
bNodeSocket *sock;
int a;
ntreeSocketUseFlags(ntree);
for(node= ntree->nodes.first; node; node= node->next) {
if(node->type==SH_NODE_TEXTURE) {
if((r_mode & R_OSA) && node->id) {