/* (C) Guenter Geiger */ #include #include #include #ifdef _MSC_VER #pragma warning( disable : 4244 ) #pragma warning( disable : 4305 ) #endif /* hacks .... this duplicates definitions in pd and must be * adjusted if something changes there !!!! */ #define EMPTYSYMBOL "emptysymbol" typedef struct _mygatom { t_text a_text; t_atom a_atom; } t_mygatom; /* this is not !! the real t_gatom ...*/ #define TATOM(a) (&((t_mygatom*)a)->a_atom) #define ATOMVAL(a) a->a_w.w_float /* glist's are not visible, but the only thing we need is to get the list link from them */ typedef struct _myglist { t_object gl_gobj; t_gobj* g_list; } t_myglist; #define FIRSTOBJECT(a) (((t_myglist*)a)->g_list) #ifndef vmess #define vmess pd_vmess #endif /* ------------------------ State ----------------------------- */ #include "envgen.h" static t_class *state_class; typedef struct _state { t_object x_obj; t_canvas* x_canvas; t_symbol* x_name; int x_slot; t_symbol* x_symslot; int x_save; int x_loading; t_clock* x_clock; } t_state; void state_dosave(t_state *x) { char name[255]; FILE* fp; t_text* a; t_symbol* dir; char dirstr[255]; #ifdef _WIN32 dir = gensym(""); #else dir = canvas_getdir(x->x_canvas); #endif strcpy(dirstr,dir->s_name); #ifndef _WIN32 strcat(dirstr,"/"); #endif if (x->x_symslot) sprintf(name,"%s%s.%s",dirstr,x->x_name->s_name,x->x_symslot->s_name); else sprintf(name,"%s%s.%d",dirstr,x->x_name->s_name,x->x_slot); fp = fopen(name,"w"); if (!fp) { post("state: unable to open %s",name); return; } a = (t_text*)FIRSTOBJECT(x->x_canvas); do { if (a->te_type == T_ATOM) { if (TATOM(a)->a_type == A_SYMBOL) { if (strlen(TATOM(a)->a_w.w_symbol->s_name)) fprintf(fp,"%s\n",atom_getsymbol(TATOM(a))->s_name); else fprintf(fp,EMPTYSYMBOL"\n"); } else { fprintf(fp,"%f\n",atom_getfloat(TATOM(a))); } } /* slider should be an atom as well ... how to do it ? */ if (!strcmp(class_getname(a->te_pd),"slider")) { fprintf(fp,"%f\n",atom_getfloat(TATOM(a))); } if (!strcmp(class_getname(a->te_pd),"sliderh")) { fprintf(fp,"%f\n",atom_getfloat(TATOM(a))); } if (!strcmp(class_getname(a->te_pd),"ticker")) { fprintf(fp,"%f\n",atom_getfloat(TATOM(a))); } #if 0 if (!strcmp(class_getname(a->te_pd),"vsl")) { /* float val = atom_getfloat(TATOM(a));*/ float val = *((float*) (((char*)a) + sizeof(t_iemgui) + sizeof(int))); fprintf(fp,"%f\n",val); fprintf(stderr,"vslider %f\n",val); } if (!strcmp(class_getname(a->te_pd),"hsl")) { float val = *((float*) (((char*)a) + sizeof(t_iemgui) + sizeof(int))); fprintf(fp,"%f\n",val); fprintf(stderr,"hslider %f\n",val); } #endif if (!strncmp(class_getname(a->te_pd),"envgen",6)) { int i; t_envgen* e = (t_envgen*) a; fprintf(fp,"%d ",e->last_state); fprintf(fp,"%f ",e->finalvalues[0]); for (i=1;i <= e->last_state;i++) fprintf(fp,"%f %f ",e->duration[i] - e->duration[i-1],e->finalvalues[i]); fprintf(fp,"\n"); } } while ((a = (t_text*)((t_gobj*)a)->g_next)); post("state saved to: %s",name); fclose(fp); } void state_save(t_state *x) { x->x_save = 1; clock_delay(x->x_clock,2000); } void state_saveoff(t_state *x) { x->x_save = 0; } void state_load(t_state *x) { char name[255]; FILE* fp; t_text* a; t_float in; t_symbol* dir; char dirstr[255]; #ifdef _WIN32 dir = gensym(""); #else dir = canvas_getdir(x->x_canvas); #endif strcpy(dirstr,dir->s_name); #ifndef _WIN32 strcat(dirstr,"/"); #endif if (x->x_symslot) sprintf(name,"%s%s.%s",dirstr,x->x_name->s_name,x->x_symslot->s_name); else sprintf(name,"%s%s.%d",dirstr,x->x_name->s_name,x->x_slot); fp = fopen(name,"r"); if (!fp) { post("state: unable to open %s",name); return; } a = (t_text*) FIRSTOBJECT(x->x_canvas); x->x_loading = 1; post("state loading from: %s",name); *name = 0; do { if (a->te_type == T_ATOM || !strcmp(class_getname(a->te_pd),"slider") || !strcmp(class_getname(a->te_pd),"ticker") || !strcmp(class_getname(a->te_pd),"sliderh") /* || !strcmp(class_getname(a->te_pd),"vsl") || !strcmp(class_getname(a->te_pd),"hsl" ) */ ) { if (TATOM(a)->a_type == A_SYMBOL) { if (fscanf(fp,"%s",name)<=0) continue; if (strcmp(name,EMPTYSYMBOL)) vmess((t_pd*)a,gensym("set"),"s",gensym(name)); } else { if (fscanf(fp,"%f",&in)<=0) continue; vmess((t_pd*)a,&s_float,"f",in); } } if (!strncmp(class_getname(a->te_pd),"envgen",6)) { int i; int end; float val; float dur; t_atom ilist[255]; fscanf(fp,"%f",&in); end = in; if (fscanf(fp,"%f",&val)<=0) continue; SETFLOAT(ilist,val); for (i=1 ;i <= end;i++) { fscanf(fp,"%f",&dur); fscanf(fp,"%f",&val); SETFLOAT(ilist +2*i-1,dur); SETFLOAT(ilist+2*i,val); } pd_typedmess((t_pd*)a,&s_list,2*end+1,ilist); // post("ok %d",end); } } while ((a = (t_text*)((t_gobj*)a)->g_next) && !feof(fp)); x->x_loading = 0; fclose(fp); } void state_float(t_state *x,t_floatarg f) { if (x->x_loading) return; x->x_symslot = NULL; x->x_slot = f; if (x->x_save) { x->x_save = 0; state_dosave(x); return; } state_load(x); outlet_float(x->x_obj.ob_outlet,x->x_slot); } void state_anything(t_state *x,t_symbol* s,t_int argc,t_atom* argv) { x->x_symslot = s; if (x->x_save) { x->x_save = 0; state_dosave(x); return; } state_load(x); outlet_symbol(x->x_obj.ob_outlet,x->x_symslot); } void state_symbol(t_state *x,t_symbol* s) { x->x_symslot = s; if (x->x_save) { x->x_save = 0; state_dosave(x); return; } state_load(x); outlet_symbol(x->x_obj.ob_outlet,x->x_symslot); } void state_bang(t_state *x) { if (x->x_symslot) outlet_symbol(x->x_obj.ob_outlet,x->x_symslot); else outlet_float(x->x_obj.ob_outlet,x->x_slot); } static void *state_new(t_symbol* name) { t_state *x = (t_state *)pd_new(state_class); x->x_canvas = canvas_getcurrent(); if (name != &s_) x->x_name = name; else x->x_name = gensym("state"); x->x_clock = clock_new(x, (t_method)state_saveoff); x->x_slot = 0; x->x_symslot = NULL; x->x_loading = 0; x->x_save = 0; outlet_new(&x->x_obj, &s_float); return (x); } void state_setup(void) { state_class = class_new(gensym("state"), (t_newmethod)state_new, 0, sizeof(t_state), 0,A_DEFSYM,0); class_addfloat(state_class,state_float); class_addmethod(state_class,(t_method) state_save, gensym("save"), 0); class_addanything(state_class,(t_method) state_anything); class_addbang(state_class,state_bang); class_addsymbol(state_class,state_symbol); /* class_addmethod(state_class, (t_method)state_load, gensym("load"), 0);*/ }