[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [30535] branches/particles-2010/source/ blender: Implemented "Any" socket type, which can be used for generic nodes .
Lukas Toenne
lukas.toenne at googlemail.com
Tue Jul 20 14:35:56 CEST 2010
Revision: 30535
http://projects.blender.org/plugins/scmsvn/viewcvs.php?view=rev&root=bf-blender&revision=30535
Author: lukastoenne
Date: 2010-07-20 14:35:56 +0200 (Tue, 20 Jul 2010)
Log Message:
-----------
Implemented "Any" socket type, which can be used for generic nodes. The socket type is resolved as soon as such a node (or subtree) gets connected to a concrete type socket. Should be used with care since generic nodes have to implement versions for all other socket types.
Modified Paths:
--------------
branches/particles-2010/source/blender/blenkernel/BKE_node.h
branches/particles-2010/source/blender/blenkernel/intern/node.c
branches/particles-2010/source/blender/editors/space_node/drawnode.c
branches/particles-2010/source/blender/editors/space_node/node_draw.c
branches/particles-2010/source/blender/editors/space_node/node_edit.c
branches/particles-2010/source/blender/makesdna/DNA_node_types.h
branches/particles-2010/source/blender/makesrna/intern/rna_nodetree.c
branches/particles-2010/source/blender/makesrna/intern/rna_nodetree_types.h
branches/particles-2010/source/blender/nodes/SIM_node.h
branches/particles-2010/source/blender/nodes/intern/SIM_nodes/SIM_debugprint.c
branches/particles-2010/source/blender/nodes/intern/SIM_nodes/SIM_if.c
branches/particles-2010/source/blender/nodes/intern/SIM_nodes/SIM_pass.c
branches/particles-2010/source/blender/nodes/intern/SIM_nodes/SIM_program.c
branches/particles-2010/source/blender/nodes/intern/SIM_nodes/SIM_subprogram.c
branches/particles-2010/source/blender/nodes/intern/SIM_util.c
branches/particles-2010/source/blender/nodes/intern/SIM_util.h
branches/particles-2010/source/blender/nodes/intern/node_tree_simulation.c
Added Paths:
-----------
branches/particles-2010/source/blender/nodes/intern/SIM_nodes/SIM_get_object_data.c
branches/particles-2010/source/blender/nodes/intern/SIM_nodes/SIM_set_object_data.c
Modified: branches/particles-2010/source/blender/blenkernel/BKE_node.h
===================================================================
--- branches/particles-2010/source/blender/blenkernel/BKE_node.h 2010-07-20 12:22:45 UTC (rev 30534)
+++ branches/particles-2010/source/blender/blenkernel/BKE_node.h 2010-07-20 12:35:56 UTC (rev 30535)
@@ -166,9 +166,11 @@
int ntreeHasType(struct bNodeTree *ntree, int type);
void ntreeSocketUseFlags(struct bNodeTree *ntree);
-void ntreeUpdateListSockets(struct bNodeTree *ntree);
void ntreeSolveOrder(struct bNodeTree *ntree);
+void ntreeUpdateListSockets(struct bNodeTree *ntree);
+void ntreeUpdateSocketTypes(struct bNodeTree *ntree);
+void ntreeUpdateLinks(struct bNodeTree *ntree);
void ntreeBeginExecTree(struct bNodeTree *ntree);
void ntreeExecTree(struct bNodeTree *ntree, void *callerdata, int thread);
@@ -205,7 +207,6 @@
struct bNodeLink *nodeAddLink(struct bNodeTree *ntree, struct bNode *fromnode, struct bNodeSocket *fromsock, struct bNode *tonode, struct bNodeSocket *tosock);
void nodeRemLink(struct bNodeTree *ntree, struct bNodeLink *link);
void nodeRemSocketLinks(struct bNodeTree *ntree, struct bNodeSocket *sock);
-void nodeCheckLink(struct bNodeLink *link);
struct bNode *nodeFindNodebyName(struct bNodeTree *ntree, const char *name);
int nodeFindNode(struct bNodeTree *ntree, struct bNodeSocket *sock, struct bNode **nodep, int *sockindex);
@@ -469,11 +470,13 @@
/* range 1 - 100 is reserved for common nodes */
/* using toolbox, we add node groups by assuming the values below don't exceed NODE_GROUP_MENU for now */
-#define SIM_NODE_PROGRAM 601
-#define SIM_NODE_SUBPROGRAM 602
-#define SIM_NODE_IF 603
-#define SIM_NODE_TIMESTEP 604
-#define SIM_NODE_PASS 605
+#define SIM_NODE_PROGRAM 601
+#define SIM_NODE_SUBPROGRAM 602
+#define SIM_NODE_IF 603
+#define SIM_NODE_TIMESTEP 604
+#define SIM_NODE_PASS 605
+#define SIM_NODE_GETOBJECTDATA 606
+#define SIM_NODE_SETOBJECTDATA 607
#define SIM_NODE_DEBUGPRINT 699
Modified: branches/particles-2010/source/blender/blenkernel/intern/node.c
===================================================================
--- branches/particles-2010/source/blender/blenkernel/intern/node.c 2010-07-20 12:22:45 UTC (rev 30534)
+++ branches/particles-2010/source/blender/blenkernel/intern/node.c 2010-07-20 12:35:56 UTC (rev 30535)
@@ -844,8 +844,8 @@
bNodeSocketType *stype;
bNodeSocket *sock, *next_sock;
- for (node = ntree->nodes.first; node; node = node->next) {
- /* nodes are presumed fully verified, stype and socket list are in sync */
+ /* nodes are presumed fully verified, stype and socket list are in sync */
+ for (node=ntree->nodes.first; node; node = node->next) {
stype= node->typeinfo->inputs;
sock= node->inputs.first;
while (sock) {
@@ -868,7 +868,7 @@
sock = sock->next;
}
}
-
+
++stype;
}
}
@@ -1093,31 +1093,47 @@
}
}
-void nodeCheckLink(bNodeLink *link)
+void ntreeUpdateLinks(bNodeTree *ntree)
{
- /* TODO this is where an actual converter matrix would come in handy - phonybone */
- int valid = 1;
- if (link->fromsock == NULL || link->tosock == NULL) {
- /* don't assume bad links when they're incomplete (e.g. in modal operator) */
- valid = 1;
- }
- else {
- int fromtype = link->fromsock->type;
- int totype = link->tosock->type;
- if (ELEM3(fromtype, SOCK_VALUE, SOCK_RGBA, SOCK_VECTOR) && ELEM3(totype, SOCK_VALUE, SOCK_RGBA, SOCK_VECTOR)) {
+ bNodeLink *link;
+
+ for (link = ntree->links.first; link; link = link->next) {
+ int valid = 1;
+ if (link->fromsock == NULL || link->tosock == NULL) {
+ /* don't assume bad links when they're incomplete (e.g. in modal operator) */
valid = 1;
- } else {
- valid = (fromtype == totype);
}
+ else {
+ int fromtype = link->fromsock->type;
+ int totype = link->tosock->type;
+ /* non-simulation sockets can convert anything */
+ if (ELEM3(fromtype, SOCK_VALUE, SOCK_RGBA, SOCK_VECTOR) && ELEM3(totype, SOCK_VALUE, SOCK_RGBA, SOCK_VECTOR)) {
+ valid = 1;
+ }
+ /* SOCK_ANY sockets adapt to the other side */
+ else if (fromtype == SOCK_ANY || totype == SOCK_ANY) {
+ valid = 1;
+ /* int and float implicitely convertible */
+ }
+ else if (ELEM(fromtype, SOCK_INT, SOCK_FLOAT) && ELEM(totype, SOCK_INT, SOCK_FLOAT)) {
+ valid = 1;
+ }
+ /* int and float can be converted to boolean */
+ else if (ELEM(fromtype, SOCK_INT, SOCK_FLOAT) && totype == SOCK_BOOL) {
+ valid = 1;
+ }
+ else {
+ valid = (fromtype == totype);
+ }
+ }
+
+ if (valid)
+ link->flag |= NLINK_VALID;
+ else
+ link->flag &= ~NLINK_VALID;
}
-
- if (valid)
- link->flag |= NLINK_VALID;
- else
- link->flag &= ~NLINK_VALID;
}
-
bNodeTree *ntreeAddTree(int type)
{
bNodeTreeTypeInfo *treetype= ntreeGetTypeInfo(type);
@@ -1766,6 +1782,104 @@
might be different for editor or for "real" use... */
}
+static int socktype_greater_than(int a, int b)
+{
+ static int prefmap[] = { 0, 6, 5, 0, 1, 2, 3, 4 };
+ return prefmap[a] > prefmap[b];
+}
+
+void ntreeUpdateSocketTypes(bNodeTree *ntree)
+{
+ bNode *node;
+ bNodeSocket *sock, *fromsock;
+ int resolved;
+
+ /* reset SOCK_ANY sockets */
+ for (node=ntree->nodes.first; node; node = node->next) {
+ for (sock= node->inputs.first; sock; sock = sock->next) {
+ if (sock->stype->type == SOCK_ANY)
+ sock->type = SOCK_ANY;
+ }
+ for (sock= node->outputs.first; sock; sock = sock->next) {
+ if (sock->stype->type == SOCK_ANY)
+ sock->type = SOCK_ANY;
+ }
+ }
+
+ /* repeat this until no more sockets can be resolved */
+ /* Note: this is kind of a brute-force approach, but it's not a speed-critical
+ * area and not extremely bad either. Also the number of nodes will probably not be
+ * big enough to make this noticable, but if necessary a breadth-first-search method
+ * to find "type islands" could be implemented later. - phonybone */
+ do {
+ resolved = 0;
+
+ /* first resolve types from outputs (left to right) */
+ for (node=ntree->nodes.first; node; node = node->next) {
+ /* only atomic nodes get resolved. */
+ if (node->type == NODE_GROUP) {
+ /* TODO */
+ }
+ else {
+ for (sock= node->inputs.first; sock; sock = sock->next) {
+ if (sock->link && sock->link->fromsock) {
+ fromsock = sock->link->fromsock;
+ if (sock->stype->type == SOCK_ANY && socktype_greater_than(fromsock->type, sock->type)) {
+ sock->type = fromsock->type;
+ ++resolved;
+ }
+ }
+ }
+ }
+ }
+ /* now resolve remaining types from inputs (right to left) */
+ for (node=ntree->nodes.last; node; node = node->prev) {
+ /* only atomic nodes get resolved. */
+ if (node->type == NODE_GROUP) {
+ /* TODO */
+ }
+ else {
+ /* choose the "best" socket type for output sockets among the linked sockets */
+ for (sock= node->inputs.first; sock; sock = sock->next) {
+ if (sock->link && sock->link->fromsock) {
+ fromsock = sock->link->fromsock;
+ if (fromsock->stype->type == SOCK_ANY && socktype_greater_than(sock->type, fromsock->type)) {
+ fromsock->type = sock->type;
+ ++resolved;
+ }
+ }
+ }
+ }
+ }
+
+ /* finally upgrade socket types if possible */
+ for (node=ntree->nodes.first; node; node = node->next) {
+ int besttype = -1;
+ for (sock= node->inputs.first; sock; sock = sock->next) {
+ if (sock->stype->type == SOCK_ANY && socktype_greater_than(sock->type, besttype))
+ besttype = sock->type;
+ }
+ for (sock= node->outputs.first; sock; sock = sock->next) {
+ if (sock->stype->type == SOCK_ANY && socktype_greater_than(sock->type, besttype))
+ besttype = sock->type;
+ }
+
+ if (besttype >= 0) {
+ for (sock= node->inputs.first; sock; sock = sock->next) {
+ if (sock->stype->type == SOCK_ANY) {
+ sock->type = besttype;
+ }
+ }
+ for (sock= node->outputs.first; sock; sock = sock->next) {
+ if (sock->stype->type == SOCK_ANY) {
+ sock->type = besttype;
+ }
+ }
+ }
+ }
+ } while (resolved > 0);
+}
+
/* Should be callback! */
/* Do not call execs here */
void NodeTagChanged(bNodeTree *ntree, bNode *node)
@@ -2504,6 +2618,8 @@
nodeRegisterType(ntypelist, &sim_node_pass);
nodeRegisterType(ntypelist, &sim_node_timestep);
nodeRegisterType(ntypelist, &sim_node_debugprint);
+ nodeRegisterType(ntypelist, &sim_node_getobjectdata);
+ nodeRegisterType(ntypelist, &sim_node_setobjectdata);
}
static void remove_dynamic_typeinfos(ListBase *list)
Modified: branches/particles-2010/source/blender/editors/space_node/drawnode.c
===================================================================
--- branches/particles-2010/source/blender/editors/space_node/drawnode.c 2010-07-20 12:22:45 UTC (rev 30534)
+++ branches/particles-2010/source/blender/editors/space_node/drawnode.c 2010-07-20 12:35:56 UTC (rev 30535)
@@ -1261,39 +1261,34 @@
}
}
-#if 0
-static void node_particles_buts_emitter(uiLayout *layout, bContext *C, PointerRNA *ptr)
+static void node_simulation_buts_getobjectdata(uiLayout *layout, bContext *C, PointerRNA *ptr)
{
- bNode *node= ptr->data;
+// bNode *node= ptr->data;
uiLayout *col;
- col= uiLayoutColumn(layout, 1);
- uiItemR(col, ptr, "emitter_index", 0, NULL, 0);
+ col= uiLayoutColumn(layout, 0);
+ uiItemR(col, ptr, "object", 0, NULL, 0);
}
-static void node_particles_buts_object(uiLayout *layout, bContext *C, PointerRNA *ptr)
+static void node_simulation_buts_setobjectdata(uiLayout *layout, bContext *C, PointerRNA *ptr)
{
- bNode *node= ptr->data;
+// bNode *node= ptr->data;
+ uiLayout *col;
- uiTemplateID(layout, C, ptr, "object", NULL, NULL, NULL);
-
- if(!node->id) return;
+ col= uiLayoutColumn(layout, 0);
+ uiItemR(col, ptr, "object", 0, NULL, 0);
}
-#endif
/* only once called */
static void node_simulation_set_butfunc(bNodeType *ntype)
{
switch(ntype->type) {
- #if 0
- case SIM_NODE_EMITTER:
- ntype->uifunc = node_simulation_buts_emitter;
+ case SIM_NODE_GETOBJECTDATA:
+ ntype->uifunc = node_simulation_buts_getobjectdata;
break;
-
- case SIM_NODE_OBJECT:
- ntype->uifunc = node_particles_buts_object;
+ case SIM_NODE_SETOBJECTDATA:
+ ntype->uifunc = node_simulation_buts_setobjectdata;
break;
- #endif
default:
ntype->uifunc= NULL;
Modified: branches/particles-2010/source/blender/editors/space_node/node_draw.c
===================================================================
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list