aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorThomas O Fredericks <mrtof@users.sourceforge.net>2009-10-24 20:51:11 +0000
committerThomas O Fredericks <mrtof@users.sourceforge.net>2009-10-24 20:51:11 +0000
commitc8fdbe3013f1ac6c7e5bca00ec57aff59d8354fd (patch)
tree53813bb68e0584da4afb8710c8478b75cbc2955a
parent7a8bdf66f6138b5e320732751a158a926dfcebb6 (diff)
Added onlyone as a replacement for destroysend
svn path=/trunk/externals/tof/; revision=12664
-rw-r--r--help/onlyone-help.pd66
-rw-r--r--src/onlyone.c188
-rw-r--r--src/param.h17
3 files changed, 257 insertions, 14 deletions
diff --git a/help/onlyone-help.pd b/help/onlyone-help.pd
new file mode 100644
index 0000000..e76eea4
--- /dev/null
+++ b/help/onlyone-help.pd
@@ -0,0 +1,66 @@
+#N canvas 1079 120 620 485 10;
+#X obj 63 213 loadbang;
+#X msg 123 213 set a;
+#X msg 165 214 set b;
+#X msg 208 215 set;
+#X obj 280 215 loadbang;
+#X msg 340 215 set a;
+#X msg 383 217 set b;
+#X msg 425 217 set;
+#X msg 297 306 1;
+#X msg 370 303 0;
+#X msg 66 299 1;
+#X msg 139 296 0;
+#X obj 67 274 bng 15 250 50 0 empty empty empty 17 7 0 10 -262144 -1
+-1;
+#X obj 138 271 bng 15 250 50 0 empty empty empty 17 7 0 10 -262144
+-1 -1;
+#X obj 296 280 bng 15 250 50 0 empty empty empty 17 7 0 10 -262144
+-1 -1;
+#X obj 367 278 bng 15 250 50 0 empty empty empty 17 7 0 10 -262144
+-1 -1;
+#X obj 62 244 tof/onlyone a;
+#X obj 294 251 tof/onlyone b;
+#X obj 39 33 cnv 15 400 100 empty empty empty 20 12 0 14 -249661 -66577
+0;
+#X text 44 84 author: mrtoftrash@gmail.com;
+#X text 44 64 tags: initialization control;
+#X text 44 105 version: 2009-10-24;
+#X text 44 33 description: makes sure it is the first or only [onlyone]
+to use that name.;
+#X text 77 399 Outlet 1: bangs if it is the first or only one to use
+that name.;
+#X text 79 431 Outlet 2: bangs if it not the the first and not the
+only one to use that name.;
+#X text 62 139 Try to "set" the name of each [onlyone] to the same
+name and than to different names.;
+#X obj 82 358 bng 15 250 50 0 empty empty empty 17 7 0 10 -262144 -1
+-1;
+#X obj 81 329 metro 500;
+#X obj 330 340 metro 500;
+#X obj 336 368 bng 15 250 50 0 empty empty empty 17 7 0 10 -262144
+-1 -1;
+#X text 65 171 If both [onlyone] have the same name \, only one metro
+will be active.;
+#X connect 0 0 16 0;
+#X connect 1 0 16 0;
+#X connect 2 0 16 0;
+#X connect 3 0 16 0;
+#X connect 4 0 17 0;
+#X connect 5 0 17 0;
+#X connect 6 0 17 0;
+#X connect 7 0 17 0;
+#X connect 8 0 28 0;
+#X connect 9 0 28 0;
+#X connect 10 0 27 0;
+#X connect 11 0 27 0;
+#X connect 12 0 10 0;
+#X connect 13 0 11 0;
+#X connect 14 0 8 0;
+#X connect 15 0 9 0;
+#X connect 16 0 12 0;
+#X connect 16 1 13 0;
+#X connect 17 0 14 0;
+#X connect 17 1 15 0;
+#X connect 27 0 26 0;
+#X connect 28 0 29 0;
diff --git a/src/onlyone.c b/src/onlyone.c
new file mode 100644
index 0000000..60287b0
--- /dev/null
+++ b/src/onlyone.c
@@ -0,0 +1,188 @@
+
+#include "m_pd.h"
+
+struct _onlyone;
+
+typedef struct _oo {
+ struct _onlyone* x;
+ //t_symbol* name;
+ struct _oo* next;
+ struct _oo* previous;
+} t_oo;
+
+static t_oo* oos = NULL;
+
+static t_class *onlyone_class;
+
+typedef struct _onlyone {
+ t_object x_obj;
+ t_outlet* outlet;
+ t_outlet* outlet2;
+ t_symbol* name;
+ int iamtheone;
+ t_symbol* s_empty;
+ //t_sample f_common;
+ //t_common* pg;
+ //t_sample f;
+} t_onlyone;
+
+
+static void onlyone_bang( t_onlyone *x) {
+ if (x->iamtheone) {
+ outlet_bang(x->outlet);
+ } else {
+ outlet_bang(x->outlet2);
+ }
+}
+
+
+static void onlyone_register(t_onlyone* x) {
+
+
+ t_oo* oo = oos;
+
+ int outputme = 1;
+
+
+ t_oo* new_oo = getbytes(sizeof(*new_oo));
+ new_oo->x = x;
+
+ if ( oo != NULL) {
+ //post("oo is not null");
+ if (outputme && (oo->x->name == x->name)) outputme = 0;
+ // Get the last oo
+ while (oo->next) {
+ oo = oo->next;
+ }
+ }
+
+ // Append
+
+ new_oo->previous = oo;
+ new_oo->next = NULL;
+ if (oo != NULL) {
+ oo->next = new_oo;
+ } else {
+ //post("Adding the first");
+ oos = new_oo;
+ }
+
+ x->iamtheone = outputme;
+
+}
+
+
+static void onlyone_unregister(t_onlyone* x) {
+
+ t_oo* oo = oos;
+
+ t_onlyone* theotherone = NULL;
+ t_oo* deleteone = NULL;
+
+ if ( oo != NULL) {
+ // Get the mathching oo and the x to output to
+ while ( oo ) {
+ if ( oo->x == x ) {
+ //post("Found oo to delete");
+ deleteone = oo;
+ } else if (x->iamtheone && theotherone==NULL && (oo->x->name == x->name) ) {
+ theotherone = oo->x;
+ }
+ if ( deleteone && theotherone) break;
+ oo = oo->next;
+ }
+
+
+
+ // Delete the oo matching the x that called this function
+ if (deleteone) {
+
+ if (deleteone->previous) {
+ deleteone->previous->next = deleteone->next;
+ if (deleteone->next) deleteone->next->previous = deleteone->previous;
+
+ } else {
+ oos = deleteone->next;
+ if ( deleteone->next != NULL) deleteone->next->previous = NULL;
+ }
+
+ freebytes(deleteone,sizeof(*deleteone));
+ x->iamtheone = 0;
+ x->name = NULL;
+ } else {
+ post("Hum, did not find oo to delete!");
+ }
+
+ // Output the bang to the other one
+ if (theotherone) {
+ theotherone->iamtheone = 1;
+ onlyone_bang(theotherone);
+ }
+
+ } else {
+ post("Weird, the list is empty...");
+ }
+
+ // if (oos==NULL) post("this is the end");
+
+}
+
+
+static void onlyone_free( t_onlyone *x) {
+
+ if ( x->name) onlyone_unregister(x);
+}
+
+static void onlyone_set( t_onlyone *x, t_symbol *s) {
+ if ( s == x->s_empty) {
+ if ( x->name) {
+ onlyone_unregister(x);
+ //onlyone_bang(x);
+ }
+ } else if ( x->name && s != x->name) {
+ onlyone_unregister(x);
+ x->name = s;
+ onlyone_register(x);
+ //onlyone_bang(x);
+ } else if ( x->name == NULL) {
+ x->name = s;
+ onlyone_register(x);
+ //onlyone_bang(x);
+ }
+ onlyone_bang(x);
+}
+
+
+
+
+static void *onlyone_new(t_symbol* s)
+{
+ t_onlyone *x = (t_onlyone *)pd_new(onlyone_class);
+
+ x->s_empty = gensym("");
+ x->iamtheone = 0;
+ x->name = NULL;
+
+ if ( s != x->s_empty) x->name = s;
+
+ x->outlet = outlet_new(&x->x_obj, &s_bang);
+
+ if ( x->name) onlyone_register(x);
+
+
+ x->outlet2 = outlet_new(&x->x_obj, &s_bang);
+
+ return (void *)x;
+}
+
+void onlyone_setup(void) {
+ onlyone_class = class_new(gensym("onlyone"),
+ (t_newmethod)onlyone_new,
+ (t_method)onlyone_free, sizeof(t_onlyone),
+ 0, A_DEFSYMBOL, 0);
+
+ class_addbang(onlyone_class, onlyone_bang);
+
+ class_addmethod(onlyone_class, (t_method)onlyone_set, gensym("set"),A_DEFSYMBOL,0);
+
+}
diff --git a/src/param.h b/src/param.h
index dfe8588..1c0b3a5 100644
--- a/src/param.h
+++ b/src/param.h
@@ -308,28 +308,17 @@ static void param_unregister(t_param* p) {
if ( paramlist) {
- //p->users = p->users - 1;
- //if ( p->users == 0 ) {
- // Remove param
- //post("Removing last param of this name");
+
if (p->previous) {
p->previous->next = p->next;
if (p->next) p->next->previous = p->previous;
- /*
- if (p->next == NULL) {
- p->previous->next = NULL;
- } else {
- p->previous->next = p->next;
- }
- */
+
} else {
paramlist = p->next;
if ( p->next != NULL) p->next->previous = NULL;
}
- //freebytes(p->av, p->alloc * sizeof *(p->av) );
- //freebytes(p->av_g, p->ac_g * sizeof *(p->av_g) );
+
freebytes(p, sizeof *p);
- //}
// Update the params for that root
if (paramlist == NULL) {