From edece44e516be164bfbfc09bf8743228bfa910d9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?IOhannes=20m=20zm=C3=B6lnig?= Date: Thu, 18 Sep 2008 12:03:49 +0000 Subject: more querying svn path=/trunk/externals/iem/iemguts/; revision=10298 --- src/canvasconnections.c | 255 ++++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 248 insertions(+), 7 deletions(-) (limited to 'src') diff --git a/src/canvasconnections.c b/src/canvasconnections.c index cebd085..85e01e9 100644 --- a/src/canvasconnections.c +++ b/src/canvasconnections.c @@ -26,6 +26,7 @@ #include "m_pd.h" #include "g_canvas.h" #include "m_imp.h" +#include int glist_getindex(t_glist *x, t_gobj *y); @@ -41,19 +42,251 @@ typedef struct _canvasconnections t_outlet *x_out; } t_canvasconnections; -static void canvasconnections_outlets(t_canvasconnections *x) +typedef struct _intvec +{ + int num_elements; /* number of valid elements in the 'elements' vector */ + int*elements; /* elements */ + int size; /* private: the full length of the 'elements' vector */ +} t_intvec; + + +static t_intvec*intvec_new(int initial_size) +{ + t_intvec*res=(t_intvec*)getbytes(sizeof(t_intvec)); + if(initial_size<1) + initial_size=32; + + res->num_elements=0; + res->size=initial_size; + res->elements=(int*)getbytes(res->size*sizeof(int)); + + return res; +} + + +static void intvec_free(t_intvec*vec) +{ + if(NULL==vec)return; + if(vec->elements) + freebytes(vec->elements, sizeof(int)*vec->size); + vec->elements=NULL; + + vec->size=0; + vec->num_elements=0; + + freebytes(vec, sizeof(t_intvec)); +} + + +static t_intvec*intvec_add(t_intvec*vec, int element) +{ + /* ensure that vector is big enough */ + if(vec->size<=vec->num_elements) { + /* resize! */ + t_intvec*vec2=intvec_new(2*vec->num_elements); + memcpy(vec2->elements, vec->elements, vec->size); + vec2->num_elements=vec->size; + intvec_free(vec); + vec=vec2; + } + + /* add the new element to the end of the vector */ + vec->elements[vec->num_elements]=element; + vec->num_elements++; + + return vec; +} + +/* just for debugging... */ +static void intvec_post(t_intvec*vec) +{ + int i=0; + post("vec: 0x%X :: 0x%X holds %d/%d elements", vec, vec->elements, vec->num_elements, vec->size); + startpost("elements:"); + for(i=0; inum_elements; i++) { + startpost(" %02d", vec->elements[i]); + } + endpost(); +} + +static t_intvec**query_inletconnections(t_canvasconnections *x, int *num_inlets) { + int i=0; + t_intvec**invecs=NULL; + int ninlets=0; + int nin=0; + + t_gobj*y; + + if(0==x->x_object || 0==x->x_parent) + return 0; + + ninlets=obj_ninlets(x->x_object); + *num_inlets=ninlets; + + + // TODO....find objects connecting TO this object + /* as Pd does not have any information about connections to inlets, + * we have to find out ourselves + * this is done by traversing all objects in the canvas and try + * to find out, whether they are connected to us! + */ + + invecs=getbytes(sizeof(t_intvec*)*ninlets); + for(i=0; ix_parent->gl_list; y; y = y->g_next) /* traverse all objects in canvas */ + { + t_object*obj=(t_object*)y; + int obj_nout=obj_noutlets(obj); + int nout=0; + for(nout=0; noutx_object) { // connected to us! + int connid = glist_getindex(x->x_parent, (t_gobj*)obj); + + // post("inlet from %d:%d to my:%d", connid, sourcewhich, which); + + /* add it to the inletconnectionlist */ + intvec_add(invecs[which], connid); + } + sourcewhich++; + } + } + } + return invecs; +} + +static void canvasconnections_queryinlets(t_canvasconnections *x) +{ + t_atom at; + int ninlets=0, i; + t_intvec**invecs=query_inletconnections(x, &ninlets); + + SETFLOAT(&at, (t_float)ninlets); + outlet_anything(x->x_out, gensym("inlets"), 1, &at); + + for(i=0; inum_elements; + t_atom*ap=getbytes(sizeof(t_atom)*(size+1)); + int j=0; + SETFLOAT(ap, (t_float)i); + for(j=0; jelements[j])); + + outlet_anything(x->x_out, gensym("inlet"), size+1, ap); + + intvec_free(invecs[i]); + freebytes(ap, sizeof(t_atom)*(size+1)); + } + if(invecs)freebytes(invecs, sizeof(t_intvec*)*ninlets); +} + +static int canvasconnections_inlets(t_canvasconnections *x) { - int noutlets=0; - int nout=0; t_atom at; + int ninlets=0; if(0==x->x_object || 0==x->x_parent) + return 0; + + ninlets=obj_ninlets(x->x_object); + + + ninlets=obj_ninlets(x->x_object); + SETFLOAT(&at, (t_float)ninlets); + outlet_anything(x->x_out, gensym("inlets"), 1, &at); + + return ninlets; +} + +static void canvasconnections_inlet(t_canvasconnections *x, t_floatarg f) +{ + int inlet=f; + t_atom at[4]; + int ninlets=0; + + t_intvec**inlets=query_inletconnections(x, &ninlets); + if(!inlets || inlet < 0 || inlet>ninlets) { + /* non-existing inlet! */ return; + } else { + post("TODO"); + + } +} + + +static int canvasconnections_outlets(t_canvasconnections *x) +{ + t_atom at; + int noutlets=0; + + if(0==x->x_object || 0==x->x_parent) + return 0; noutlets=obj_noutlets(x->x_object); SETFLOAT(&at, (t_float)noutlets); - outlet_anything(x->x_out, gensym("outlets"), 1, &at); + + return noutlets; +} + +static void canvasconnections_outlet(t_canvasconnections *x, t_floatarg f) +{ + int outlet=f; + t_atom at[4]; + int noutlets=0; + + if(0==x->x_object || 0==x->x_parent) + return; + + noutlets=obj_noutlets(x->x_object); + + if(outlet<0 || outlet>=noutlets) { + post("nonexisting outlet: %d", outlet); + /* non-existing outlet! */ + return; + } else { + t_outlet*out=0; + t_outconnect*conn=obj_starttraverseoutlet(x->x_object, &out, outlet); + t_object*dest=0; + t_inlet*in=0; + int count=0; + int id=glist_getindex(x->x_parent, (t_gobj*)x->x_object); + + conn=obj_starttraverseoutlet(x->x_object, &out, outlet); + while(conn) { + int destid=0; + int destwhich=0; + conn=obj_nexttraverseoutlet(conn, &dest, &in, &destwhich); + destid = glist_getindex(x->x_parent, (t_gobj*)dest); + + //post("connection from %d|%d to %d|%d", id, outlet, destid, destwhich); + SETFLOAT(at+0, (t_float)id); + SETFLOAT(at+1, (t_float)outlet); + SETFLOAT(at+2, (t_float)destid); + SETFLOAT(at+3, (t_float)destwhich); + + outlet_anything(x->x_out, gensym("outconnect"), 4, at); + } + } + +} + +static void canvasconnections_queryoutlets(t_canvasconnections *x) +{ + int noutlets=canvasconnections_outlets(x); + int nout=0; + t_atom at; for(nout=0; noutx_object, &out, nout); @@ -70,10 +303,11 @@ static void canvasconnections_outlets(t_canvasconnections *x) SETFLOAT(abuf, nout); conn=obj_starttraverseoutlet(x->x_object, &out, nout); while(conn) { - t_float connid=0; + int connid=0; conn=obj_nexttraverseoutlet(conn, &dest, &in, &which); connid = glist_getindex(x->x_parent, (t_gobj*)dest); - SETFLOAT(abuf+1+i, connid); + + SETFLOAT(abuf+1+i, (t_float)connid); i++; } outlet_anything(x->x_out, gensym("outlet"), count+1, abuf); @@ -83,7 +317,8 @@ static void canvasconnections_outlets(t_canvasconnections *x) static void canvasconnections_bang(t_canvasconnections *x) { - canvasconnections_outlets(x); + canvasconnections_queryinlets(x); + canvasconnections_queryoutlets(x); } @@ -127,4 +362,10 @@ void canvasconnections_setup(void) sizeof(t_canvasconnections), 0, A_DEFFLOAT, 0); class_addbang(canvasconnections_class, (t_method)canvasconnections_bang); + + class_addmethod(canvasconnections_class, (t_method)canvasconnections_outlets, gensym("outlets"), 0); + class_addmethod(canvasconnections_class, (t_method)canvasconnections_outlet, gensym("outlet"), A_FLOAT, 0); + + class_addmethod(canvasconnections_class, (t_method)canvasconnections_inlets, gensym("inlets"), 0); + class_addmethod(canvasconnections_class, (t_method)canvasconnections_inlet, gensym("inlet"), A_FLOAT, 0); } -- cgit v1.2.1