aboutsummaryrefslogtreecommitdiff
path: root/pd
diff options
context:
space:
mode:
authorMiller Puckette <millerpuckette@users.sourceforge.net>2005-08-19 23:28:03 +0000
committerMiller Puckette <millerpuckette@users.sourceforge.net>2005-08-19 23:28:03 +0000
commitd6a71adae7c90224e2a49f0edcd4fd52fa0a1b30 (patch)
tree3ff96fa9bd7aceaeb5c832c097788c80a98bee17 /pd
parent8892fb6aabcbfd2c4695c154c22751b5fe5c9004 (diff)
Version 0.39-0test5. Bug fixes and more care about closing dirty windows
and quitting. svn path=/trunk/; revision=3434
Diffstat (limited to 'pd')
-rw-r--r--pd/src/d_misc.c17
-rw-r--r--pd/src/d_soundfile.c38
-rw-r--r--pd/src/d_ugen.c13
-rw-r--r--pd/src/g_array.c19
-rw-r--r--pd/src/g_canvas.c2
-rw-r--r--pd/src/g_canvas.h6
-rw-r--r--pd/src/g_editor.c86
-rw-r--r--pd/src/g_template.c4
-rw-r--r--pd/src/g_text.c2
-rw-r--r--pd/src/m_glob.c4
-rw-r--r--pd/src/m_imp.h2
-rw-r--r--pd/src/m_pd.h1
-rw-r--r--pd/src/makefile2
-rw-r--r--pd/src/notes.txt62
-rw-r--r--pd/src/s_inter.c20
-rw-r--r--pd/src/s_main.c2
-rw-r--r--pd/src/s_midi_alsa.c4
-rw-r--r--pd/src/t_tkcmd.c2
-rw-r--r--pd/src/u_main.tk67
-rw-r--r--pd/src/x_list.c5
20 files changed, 256 insertions, 102 deletions
diff --git a/pd/src/d_misc.c b/pd/src/d_misc.c
index ea96c5ac..1056f0cb 100644
--- a/pd/src/d_misc.c
+++ b/pd/src/d_misc.c
@@ -134,11 +134,24 @@ static t_class *samplerate_tilde_class;
typedef struct _samplerate
{
t_object x_obj;
+ float x_sr;
} t_samplerate;
static void samplerate_tilde_bang(t_samplerate *x)
{
- outlet_float(x->x_obj.ob_outlet, sys_getsr());
+ if (!canvas_dspstate)
+ {
+ post(
+ "NB: samplerate~ momentarily started DSP to learn sample rate");
+ canvas_resume_dsp(1);
+ canvas_suspend_dsp();
+ }
+ outlet_float(x->x_obj.ob_outlet, x->x_sr);
+}
+
+static void samplerate_tilde_dsp(t_samplerate *x, t_signal **sp)
+{
+ x->x_sr = sp[0]->s_sr;
}
static void *samplerate_tilde_new(t_symbol *s)
@@ -153,6 +166,8 @@ static void samplerate_tilde_setup(void)
samplerate_tilde_class = class_new(gensym("samplerate~"),
(t_newmethod)samplerate_tilde_new, 0, sizeof(t_samplerate), 0, 0);
class_addbang(samplerate_tilde_class, samplerate_tilde_bang);
+ class_addmethod(samplerate_tilde_class, (t_method)samplerate_tilde_dsp,
+ gensym("dsp"), A_CANT, 0);
}
/* ------------------------ global setup routine ------------------------- */
diff --git a/pd/src/d_soundfile.c b/pd/src/d_soundfile.c
index 07e0635b..0ec2c2af 100644
--- a/pd/src/d_soundfile.c
+++ b/pd/src/d_soundfile.c
@@ -1976,13 +1976,34 @@ static void *writesf_child_main(void *zz)
x->x_requestcode = REQUEST_BUSY;
x->x_fileerror = 0;
- /* if there's already a file open, close it */
+ /* if there's already a file open, close it. This
+ should never happen since writesf_open() calls stop if
+ needed and then waits until we're idle. */
if (x->x_fd >= 0)
{
+ int bytesperframe = x->x_bytespersample * x->x_sfchannels;
+ int bigendian = x->x_bigendian;
+ char *filename = x->x_filename;
+ int fd = x->x_fd;
+ int filetype = x->x_filetype;
+ int itemswritten = x->x_itemswritten;
+ int swap = x->x_swap;
pthread_mutex_unlock(&x->x_mutex);
- close (x->x_fd);
+
+ soundfile_finishwrite(x, filename, fd,
+ filetype, 0x7fffffff, itemswritten,
+ bytesperframe, swap);
+ close (fd);
+
pthread_mutex_lock(&x->x_mutex);
x->x_fd = -1;
+#ifdef DEBUG_SOUNDFILE
+ {
+ char s[1000];
+ sprintf(s, "bug??? ditched %d\n", itemswritten);
+ pute(s);
+ }
+#endif
if (x->x_requestcode != REQUEST_BUSY)
continue;
}
@@ -2087,9 +2108,9 @@ static void *writesf_child_main(void *zz)
}
x->x_itemswritten +=
sysrtn / (x->x_bytespersample * x->x_sfchannels);
- sprintf(boo, "after: head %d, tail %d\n",
- x->x_fifohead, x->x_fifotail);
#ifdef DEBUG_SOUNDFILE
+ sprintf(boo, "after: head %d, tail %d written %d\n",
+ x->x_fifohead, x->x_fifotail, x->x_itemswritten);
pute(boo);
#endif
/* signal parent in case it's waiting for data */
@@ -2263,6 +2284,10 @@ static void writesf_open(t_writesf *x, t_symbol *s, int argc, t_atom *argv)
int filetype, bytespersamp, swap, bigendian, normalize;
long onset, nframes;
float samplerate;
+ if (x->x_state != STATE_IDLE)
+ {
+ writesf_stop(x);
+ }
if (soundfiler_writeargparse(x, &argc,
&argv, &filesym, &filetype, &bytespersamp, &swap, &bigendian,
&normalize, &onset, &nframes, &samplerate))
@@ -2276,6 +2301,11 @@ static void writesf_open(t_writesf *x, t_symbol *s, int argc, t_atom *argv)
if (argc)
pd_error(x, "extra argument(s) to writesf~: ignored");
pthread_mutex_lock(&x->x_mutex);
+ while (x->x_requestcode != REQUEST_NOTHING)
+ {
+ sfread_cond_signal(&x->x_requestcondition);
+ sfread_cond_wait(&x->x_answercondition, &x->x_mutex);
+ }
x->x_bytespersample = bytespersamp;
x->x_swap = swap;
x->x_bigendian = bigendian;
diff --git a/pd/src/d_ugen.c b/pd/src/d_ugen.c
index 124631e6..17a4ecc3 100644
--- a/pd/src/d_ugen.c
+++ b/pd/src/d_ugen.c
@@ -660,7 +660,7 @@ static void ugen_doit(t_dspcontext *dc, t_ugenbox *u)
t_siginlet *uin;
t_sigoutconnect *oc, *oc2;
t_class *class = pd_class(&u->u_obj->ob_pd);
- int i, n;
+ int i, n, totnsig;
/* suppress creating new signals for the outputs of signal
inlets and subpatchs; except in the case we're an inlet and "blocking"
is set. We don't yet know if a subcanvas will be "blocking" so there
@@ -695,7 +695,8 @@ static void ugen_doit(t_dspcontext *dc, t_ugenbox *u)
s3->s_refcount = 1;
}
}
- insig = (t_signal **)getbytes((u->u_nin + u->u_nout) * sizeof(t_signal *));
+ totnsig = u->u_nin + u->u_nout;
+ insig = (t_signal **)getbytes((totnsig ? totnsig : 1) * sizeof(t_signal *));
outsig = insig + u->u_nin;
for (sig = insig, uin = u->u_in, i = u->u_nin; i--; sig++, uin++)
{
@@ -730,6 +731,11 @@ static void ugen_doit(t_dspcontext *dc, t_ugenbox *u)
*sig = uout->o_signal = signal_new(dc->dc_vecsize, dc->dc_srate);
(*sig)->s_refcount = uout->o_nconnect;
}
+ /* if thre are no input or output signals, supply one fake signal so
+ the object can learn the sample rate and block size. Used by the
+ samplerate~ object. */
+ if (!totnsig)
+ insig[0] = signal_new(dc->dc_vecsize, dc->dc_srate);
/* now call the DSP scheduling routine for the ugen. This
routine must fill in "borrowed" signal outputs in case it's either
a subcanvas or a signal inlet. */
@@ -744,6 +750,9 @@ static void ugen_doit(t_dspcontext *dc, t_ugenbox *u)
if (!(*sig)->s_refcount)
signal_makereusable(*sig);
}
+ /* special case: no inputs or outputs: free the fake signal we made */
+ if (!totnsig)
+ signal_makereusable(insig[0]);
if (ugen_loud)
{
if (u->u_nin + u->u_nout == 0) post("put %s %d",
diff --git a/pd/src/g_array.c b/pd/src/g_array.c
index fb11715b..cf577010 100644
--- a/pd/src/g_array.c
+++ b/pd/src/g_array.c
@@ -429,6 +429,14 @@ void garray_arraydialog(t_garray *x, t_symbol *name, t_floatarg fsize,
pd_unbind(&x->x_gobj.g_pd, x->x_realname);
x->x_realname = canvas_realizedollar(x->x_glist, argname);
pd_bind(&x->x_gobj.g_pd, x->x_realname);
+ /* redraw the whole glist, just so the name change shows up */
+ if (x->x_glist->gl_havewindow)
+ canvas_redraw(x->x_glist);
+ else if (glist_isvisible(x->x_glist->gl_owner))
+ {
+ gobj_vis(&x->x_glist->gl_gobj, x->x_glist->gl_owner, 0);
+ gobj_vis(&x->x_glist->gl_gobj, x->x_glist->gl_owner, 1);
+ }
}
size = fsize;
if (size < 1)
@@ -448,7 +456,7 @@ void garray_arraydialog(t_garray *x, t_symbol *name, t_floatarg fsize,
/* jsarlo { */
void garray_arrayviewlist_new(t_garray *x)
{
- int i, xonset, yonset, type, elemsize;
+ int i, xonset=0, yonset=0, type=0, elemsize=0;
float yval;
char cmdbuf[200];
t_symbol *arraytype;
@@ -480,7 +488,7 @@ void garray_arrayviewlist_new(t_garray *x)
void garray_arrayviewlist_fillpage(t_garray *x,
t_float page)
{
- int i, xonset, yonset, type, elemsize;
+ int i, xonset=0, yonset=0, type=0, elemsize=0;
float yval;
char cmdbuf[200];
t_symbol *arraytype;
@@ -751,11 +759,8 @@ int array_doclick(t_array *array, t_glist *glist, t_scalar *sc, t_array *ap,
&xonset, &yonset, &wonset))
{
float best = 100;
- int incr;
- /* if it has more than 2000 points, just check 300 of them. */
- if (array->a_n < 2000)
- incr = 1;
- else incr = array->a_n / 300;
+ /* if it has more than 2000 points, just check 1000 of them. */
+ int incr = (array->a_n <= 2000 ? 1 : array->a_n / 1000);
for (i = 0; i < array->a_n; i += incr)
{
float pxpix, pypix, pwpix, dx, dy;
diff --git a/pd/src/g_canvas.c b/pd/src/g_canvas.c
index adccb788..4019807f 100644
--- a/pd/src/g_canvas.c
+++ b/pd/src/g_canvas.c
@@ -36,7 +36,7 @@ struct _canvasenvironment
extern t_pd *newest;
t_class *canvas_class;
-static int canvas_dspstate; /* whether DSP is on or off */
+int canvas_dspstate; /* whether DSP is on or off */
t_canvas *canvas_editing; /* last canvas to start text edting */
t_canvas *canvas_whichfind; /* last canvas we did a find in */
t_canvas *canvas_list; /* list of all root canvases */
diff --git a/pd/src/g_canvas.h b/pd/src/g_canvas.h
index 857df86d..c8fb9979 100644
--- a/pd/src/g_canvas.h
+++ b/pd/src/g_canvas.h
@@ -583,7 +583,7 @@ EXTERN void template_setsymbol(t_template *x, t_symbol *fieldname,
EXTERN t_template *gtemplate_get(t_gtemplate *x);
EXTERN t_template *template_findbyname(t_symbol *s);
EXTERN t_canvas *template_findcanvas(t_template *tmpl);
-EXTERN void template_notify(t_template *,
+EXTERN void template_notify(t_template *template,
t_symbol *s, int argc, t_atom *argv);
EXTERN t_float template_getfloat(t_template *x, t_symbol *fieldname,
@@ -594,9 +594,9 @@ EXTERN t_symbol *template_getsymbol(t_template *x, t_symbol *fieldname,
t_word *wp, int loud);
EXTERN void template_setsymbol(t_template *x, t_symbol *fieldname,
t_word *wp, t_symbol *s, int loud);
-EXTERN t_float fielddesc_getcoord(t_fielddesc *f, t_template *,
+EXTERN t_float fielddesc_getcoord(t_fielddesc *f, t_template *template,
t_word *wp, int loud);
-EXTERN void fielddesc_setcoord(t_fielddesc *f, t_template *,
+EXTERN void fielddesc_setcoord(t_fielddesc *f, t_template *template,
t_word *wp, float pix, int loud);
EXTERN t_float fielddesc_cvttocoord(t_fielddesc *f, float val);
EXTERN float fielddesc_cvtfromcoord(t_fielddesc *f, float coord);
diff --git a/pd/src/g_editor.c b/pd/src/g_editor.c
index 932a5413..938842a6 100644
--- a/pd/src/g_editor.c
+++ b/pd/src/g_editor.c
@@ -1043,7 +1043,7 @@ void canvas_doclick(t_canvas *x, int xpos, int ypos, int which,
{
t_gobj *y;
int shiftmod, runmode, altmod, doublemod = 0, rightclick;
- int x1, y1, x2, y2, clickreturned = 0;
+ int x1=0, y1=0, x2=0, y2=0, clickreturned = 0;
if (!x->gl_editor)
{
@@ -1267,9 +1267,9 @@ int canvas_isconnected (t_canvas *x, t_text *ob1, int n1,
void canvas_doconnect(t_canvas *x, int xpos, int ypos, int which, int doit)
{
- int x11, y11, x12, y12;
+ int x11=0, y11=0, x12=0, y12=0;
t_gobj *y1;
- int x21, y21, x22, y22;
+ int x21=0, y21=0, x22=0, y22=0;
t_gobj *y2;
int xwas = x->gl_editor->e_xwas,
ywas = x->gl_editor->e_ywas;
@@ -1628,14 +1628,80 @@ void canvas_print(t_canvas *x, t_symbol *s)
else sys_vgui(".x%lx.c postscript -file x.ps\n", x);
}
-void canvas_menuclose(t_canvas *x, t_floatarg force)
+ /* find a dirty sub-glist, if any, of this one (including itself) */
+static t_glist *glist_finddirty(t_glist *x)
{
- if (x->gl_owner)
- canvas_vis(x, 0);
- else if ((force != 0) || (!x->gl_dirty))
+ t_gobj *g;
+ t_glist *g2;
+ if (x->gl_env && x->gl_dirty)
+ return (x);
+ for (g = x->gl_list; g; g = g->g_next)
+ if (pd_class(&g->g_pd) == canvas_class &&
+ (g2 = glist_finddirty((t_glist *)g)))
+ return (g2);
+ return (0);
+}
+
+ /* quit, after calling glist_finddirty() on all toplevels and verifying
+ the user really wants to discard changes */
+void glob_verifyquit(void *dummy, t_floatarg f)
+{
+ t_glist *g, *g2;
+ /* find all root canvases */
+ for (g = canvas_list; g; g = g->gl_next)
+ if (g2 = glist_finddirty(g))
+ {
+ canvas_vis(g2, 1);
+ sys_vgui(
+"pdtk_check {Discard changes to this window??} {.x%lx menuclose 3;\n} no\n",
+ g2);
+ return;
+ }
+ if (f == 0)
+ sys_vgui("pdtk_check {really quit?} {pd quit;\n} yes\n");
+ else glob_quit(0);
+}
+
+ /* close a window (or possibly quit Pd), checking for dirty flags.
+ The "force" parameter is interpreted as follows:
+ 0 - request from GUI to close, verifying whether clean or dirty
+ 1 - request from GUI to close, no verification
+ 2 - verified - mark this one clean, then continue as in 1
+ 3 - verified - mark this one clean, then verify-and-quit
+ */
+void canvas_menuclose(t_canvas *x, t_floatarg fforce)
+{
+ int force = fforce;
+ t_glist *g;
+ if (x->gl_owner && (force == 0 || force == 1))
+ canvas_vis(x, 0); /* if subpatch, just invis it */
+ else if (force == 0)
+ {
+ g = glist_finddirty(x);
+ if (g)
+ {
+ canvas_vis(g, 1);
+ sys_vgui(
+"pdtk_check {Discard changes to this window??} {.x%lx menuclose 2;\n} no\n",
+ g);
+ return;
+ }
+ else pd_free(&x->gl_pd);
+ }
+ else if (force == 1)
pd_free(&x->gl_pd);
- else sys_vgui("pdtk_check {This window has been modified. Close anyway?}\
- {.x%lx menuclose 1;\n}\n", x);
+ else if (force == 2)
+ {
+ canvas_dirty(x, 0);
+ while (x->gl_owner)
+ x = x->gl_owner;
+ canvas_menuclose(x, 0);
+ }
+ else if (force == 3)
+ {
+ canvas_dirty(x, 0);
+ glob_verifyquit(0, 1);
+ }
}
/* put up a dialog which may call canvas_font back to do the work */
@@ -1674,7 +1740,7 @@ static int canvas_dofind(t_canvas *x, int *myindex1p)
canvas_find_index1 = myindex1;
canvas_find_index2 = myindex2;
glist_noselect(x);
- canvas_vis(x, 1);
+ vmess(&x->gl_pd, gensym("menu-open"), "");
canvas_editmode(x, 1.);
glist_select(x, y);
return (1);
diff --git a/pd/src/g_template.c b/pd/src/g_template.c
index 69f1c864..b1046447 100644
--- a/pd/src/g_template.c
+++ b/pd/src/g_template.c
@@ -1524,7 +1524,9 @@ static void plot_getrect(t_gobj *z, t_glist *glist,
xfielddesc, yfielddesc, wfielddesc,
&xonset, &yonset, &wonset))
{
- for (i = 0, xsum = 0; i < array->a_n; i++)
+ /* if it has more than 2000 points, just check 1000 of them. */
+ int incr = (array->a_n <= 2000 ? 1 : array->a_n / 1000);
+ for (i = 0, xsum = 0; i < array->a_n; i += incr)
{
float usexloc, useyloc;
t_gobj *y;
diff --git a/pd/src/g_text.c b/pd/src/g_text.c
index 54b7ac37..ed37ca40 100644
--- a/pd/src/g_text.c
+++ b/pd/src/g_text.c
@@ -347,10 +347,10 @@ static void message_addsemi(t_message *x)
static void message_adddollar(t_message *x, t_floatarg f)
{
+ t_atom a;
int n = f;
if (n < 0)
n = 0;
- t_atom a;
SETDOLLAR(&a, n);
binbuf_add(x->m_text.te_binbuf, 1, &a);
glist_retext(x->m_glist, &x->m_text);
diff --git a/pd/src/m_glob.c b/pd/src/m_glob.c
index bcd9d6f3..aca3bf24 100644
--- a/pd/src/m_glob.c
+++ b/pd/src/m_glob.c
@@ -12,7 +12,7 @@ static t_class *maxclass;
over. Some others are prototyped in m_imp.h as well. */
void glob_setfilename(void *dummy, t_symbol *name, t_symbol *dir);
-void glob_quit(void *dummy);
+void glob_verifyquit(void *dummy, t_floatarg f);
void glob_dsp(void *dummy, t_symbol *s, int argc, t_atom *argv);
void glob_meters(void *dummy, t_floatarg f);
void glob_key(void *dummy, t_symbol *s, int ac, t_atom *av);
@@ -79,6 +79,8 @@ void glob_init(void)
class_addmethod(glob_pdobject, (t_method)glob_evalfile, gensym("open"),
A_SYMBOL, A_SYMBOL, 0);
class_addmethod(glob_pdobject, (t_method)glob_quit, gensym("quit"), 0);
+ class_addmethod(glob_pdobject, (t_method)glob_verifyquit,
+ gensym("verifyquit"), A_DEFFLOAT, 0);
class_addmethod(glob_pdobject, (t_method)glob_foo, gensym("foo"), A_GIMME, 0);
class_addmethod(glob_pdobject, (t_method)glob_dsp, gensym("dsp"), A_GIMME, 0);
class_addmethod(glob_pdobject, (t_method)glob_meters, gensym("meters"),
diff --git a/pd/src/m_imp.h b/pd/src/m_imp.h
index e82d103a..d129bdbe 100644
--- a/pd/src/m_imp.h
+++ b/pd/src/m_imp.h
@@ -77,6 +77,6 @@ EXTERN int obj_sigoutletindex(t_object *x, int m);
/* misc */
EXTERN void glob_evalfile(t_pd *ignore, t_symbol *name, t_symbol *dir);
EXTERN void glob_initfromgui(void *dummy, t_symbol *s, int argc, t_atom *argv);
-
+EXTERN void glob_quit(void *dummy);
#define __m_imp_h_
#endif /* __m_imp_h_ */
diff --git a/pd/src/m_pd.h b/pd/src/m_pd.h
index 234ee3d7..41e0ffae 100644
--- a/pd/src/m_pd.h
+++ b/pd/src/m_pd.h
@@ -515,6 +515,7 @@ EXTERN float *cos_table;
EXTERN int canvas_suspend_dsp(void);
EXTERN void canvas_resume_dsp(int oldstate);
EXTERN void canvas_update_dsp(void);
+EXTERN int canvas_dspstate;
/* up/downsampling */
typedef struct _resample
diff --git a/pd/src/makefile b/pd/src/makefile
index 9a560285..433bbb6c 100644
--- a/pd/src/makefile
+++ b/pd/src/makefile
@@ -24,7 +24,7 @@ WARN_CFLAGS = -Wall -W -Wstrict-prototypes \
-Wno-unused -Wno-parentheses -Wno-switch
ARCH_CFLAGS = -DPD
-CFLAGS = -Werror $(ARCH_CFLAGS) $(WARN_CFLAGS) $(OPT_CFLAGS) $(MORECFLAGS)
+CFLAGS = -Werror -Wdeclaration-after-statement $(ARCH_CFLAGS) $(WARN_CFLAGS) $(OPT_CFLAGS) $(MORECFLAGS)
# the sources
diff --git a/pd/src/notes.txt b/pd/src/notes.txt
index dd9e641c..49f5a90c 100644
--- a/pd/src/notes.txt
+++ b/pd/src/notes.txt
@@ -20,88 +20,77 @@ Mac to tcl/tk 8.4.5; pd extension added automatically
bug fix writing aiff gfiles
bug fix (tcl error messages when starting open dialogs)
pointer rewind (also check if send-window documented?)
-
-
------------- 0.39 ---------
-problems:
-"list" to signal inlet (e.g., "*~") complains
-"find" doesn't open GOPs correctly
+stop vis-ing subpatches of abstractions
save dirty abstractions on close
close dirty patches on quit
-stop vis-ing subpatches of abstractions
-when retyping abstractions, offer to save dirty one
-don't filter locked click() through getrect
-better hit detection (getrect is too greedy; try just sending it through)
+"find" fixed to open GOPs correctly
+cheat to speed up mouse motion over arrays
+fix samplerate~ to figure out blocking
thread-unsafe callbacks from sys_microsleep()
+writesf -- "open" without "0" misses closing the previous file.
+
+------------ 0.39 ---------
windows:
modal dialogs confuse watchdog
check the right-click-on-empty-canvas
mac:
load libraries first before opening patches on drag-and-drop
- writing 3-byte soundfiles distorts???
check:
MIDI I/O for windows
blechman patch for s_inter.c
check what happens when going back and forth between graph-on-parent
-array_resize etc., should redraw the array directly? Or should "setsize"
- and "garray_resize" do it instead? check it's queued correctly.
doc:
+object list
document env~ second argument (and why is it no less than 1/10 of first???)
vibrato example
block resampling arguments
document tabwrite~_start
+"list" to signal inlet (e.g., "*~") or float inlet (f) complains.
problems:
+don't filter locked click() through getrect
+better scalar hit detection (getrect is too greedy)
+when retyping abstractions, offer to save dirty one
+should linux stop grabbing focus on vis? Is there a way to detect whether
+ the mouse is in a window when it opens?
TK commands to nonexistent windows? (occasionally still happens)
-array name changes don't show up on parent
arrays that don't fit in bounds don't update (same as red rectangle problem?)
look in d_resample.pd to understand inlet~ upsampling...
-flag for array to suppress printing name
-fix samplerate~ to figure out blocking
patcher inlets don't deal with scalars (zbug.pd)
check if there's a problem loading libs on startup if superuser
-tk errors for large tables?
-wierdly small hotspot on lines
'[' in numbox label breaks it (Yury Sept. 3)
-soundfiles with 3-byte samples buzz for the first readsf buffer (bug/x.pd)
read xx.txt in "bad" gives warnings
-writesf -- "open" without "0" misses closing the previous file.
-Also writesf~ acts differently if DSP is off when "open" is sent?
qlist - 'next 1' seems not to work
Krzysztof's qlist_next reentrancy bug
don't draw in/outlets on gui objects in graph-on-parent
reasonable font size default for GUIs
moving a bang toward top of window creates problem (invisible label)
get rid of messages causing renaming; try to prevent patches closing themselves.
-dac~/ adc~/ block~ incompatibility
scofo reports error on reading score1.txt
loading e-mailed patches without removing headers crashes pd
pd $1 bug ($1 is saved as it was evaluated, not as '$1')
check if _vsnprintf with zero argument in windows works any better...
+detect adc~ and dac~ reblocking
features:
flag to suppress printing array name above graph
+flag to suppress scrollbars in canvases
fix copyright notices
-IEM guis to use queued updates
pixel font sizes
pd to find running ones (pd -new to defeat)
rename windowname-pd instead of pd-windowname
-"enter" into object box to create new one (also, changing borders? forking?)
-tab to jump to a connected object (first one?) (shift-tab to back up?)
tables:
if there's just one array, don't do stringent hit check.
array click protection (Krzysztof's suggestion)
make graph labels persistent and add to dialog
object to get/set table size; random; quantile
flag to hide array names
-queued graphics updates for IEMGUIs and scalars
think of a way to embed abstractions in a patch
make watchdog work for MACOSX
search path to include both calling patch and abstraction, if different
-abstraction reload shouldn't have to vis everyone
pasting should look at current mouse location
delete-in-rectangle message to Pds
put serial object in main dist (see rat@telecoma, Apr. 25; winfried May 22)
@@ -109,6 +98,14 @@ open/save panel to take messages to init directory, and to set extent list
flags to defeat pre-loading specified classes
expr to parse exponential notation
pipe to handle symbols&pointers (just takes floats now???)
+editing:
+ "enter" into object box to create new one (also, change border? forking?)
+ tab to jump to a connected object (first one?) (shift-tab to back up?)
+ arrow keys to shift connections left and right
+ menu item to connect selected objects
+ highlight connections (and I/Os) on mouse motion
+ select line and hit "insert" to interpolate an object
+ option-drag an outlet to make a new, connected object
data:
data copy/paste doesn't check templates aren't changed
@@ -146,31 +143,20 @@ look at prctl(2) for FP exception handling
??? have a way to disambiguate externs from different libs???
netsend separate thread
netreceive (and netsend?) message to set port number
-think about x and y scale preservation when changing between graph and object
-show outlines of objects even when graph is "open"
graph_vis() to decorate graphs when they're toplevel (parent_glist == 0)
-get graphs to expand to hold their contents
suita.chopin.edu.pl/~czaja/miXed/externs/xeq.html -- MIDI file reader
in glist_delete, consider why this can't be just "vis 0" -- why do we need it?
closebang
check that -blocksize really reflects in audiobuf calc for Hammerfall
makefile to have make install depend on make local.
Float method for random
-figure out list, message objects
put in something for tilde order forcing
extensible "toolbar" so people can add external GUI objects
-allow spaces in paths
variable send and receive -- check how max/MSP does it?
number boxes to darken for typing and/or received messages
-dialog to change lib flag and path
pique~ and fiddle~ unification (notice pique filtering is different!)
new message box look
figure out what to do when "pd sym" conflicts with window title as in Pluton?
-
-MAX compatibilty:
-trigger 1 (on Pd, outputs 0; on Max?)
-
-LATER
bonk~ file path handling
unify arrays and garrays
dialog to give values of $1, ... for the canvas
diff --git a/pd/src/s_inter.c b/pd/src/s_inter.c
index f77b5e84..814e2834 100644
--- a/pd/src/s_inter.c
+++ b/pd/src/s_inter.c
@@ -174,7 +174,13 @@ static int sys_domicrosleep(int microsec, int pollem)
for (i = 0; i < sys_nfdpoll; i++)
if (FD_ISSET(sys_fdpoll[i].fdp_fd, &readset))
{
+#ifdef THREAD_LOCKING
+ sys_lock();
+#endif
(*sys_fdpoll[i].fdp_fn)(sys_fdpoll[i].fdp_ptr, sys_fdpoll[i].fdp_fd);
+#ifdef THREAD_LOCKING
+ sys_unlock();
+#endif
didsomething = 1;
}
return (didsomething);
@@ -280,10 +286,12 @@ void sys_set_priority(int higher)
#ifdef _POSIX_MEMLOCK
/* tb: force memlock to physical memory { */
- struct rlimit mlock_limit;
- mlock_limit.rlim_cur=0;
- mlock_limit.rlim_max=0;
- setrlimit(RLIMIT_MEMLOCK,&mlock_limit);
+ {
+ struct rlimit mlock_limit;
+ mlock_limit.rlim_cur=0;
+ mlock_limit.rlim_max=0;
+ setrlimit(RLIMIT_MEMLOCK,&mlock_limit);
+ }
/* } tb */
if (mlockall(MCL_FUTURE) != -1)
fprintf(stderr, "memory locking enabled.\n");
@@ -1087,7 +1095,7 @@ int sys_startgui(const char *guidir)
sys_guicmd = cmdbuf;
}
if (sys_verbose) fprintf(stderr, "%s", sys_guicmd);
- execl("/bin/sh", "sh", "-c", sys_guicmd, 0);
+ execl("/bin/sh", "sh", "-c", sys_guicmd, (char*)0);
perror("pd: exec");
_exit(1);
}
@@ -1171,7 +1179,7 @@ int sys_startgui(const char *guidir)
sprintf(cmdbuf, "%s/pd-watchdog\n", guidir);
if (sys_verbose) fprintf(stderr, "%s", cmdbuf);
- execl("/bin/sh", "sh", "-c", cmdbuf, 0);
+ execl("/bin/sh", "sh", "-c", cmdbuf, (char*)0);
perror("pd: exec");
_exit(1);
}
diff --git a/pd/src/s_main.c b/pd/src/s_main.c
index 098ca115..79e5e153 100644
--- a/pd/src/s_main.c
+++ b/pd/src/s_main.c
@@ -2,7 +2,7 @@
* For information on usage and redistribution, and for a DISCLAIMER OF ALL
* WARRANTIES, see the file, "LICENSE.txt," in this distribution. */
-char pd_version[] = "Pd version 0.39 TEST 4c\n";
+char pd_version[] = "Pd version 0.39 TEST 5\n";
char pd_compiletime[] = __TIME__;
char pd_compiledate[] = __DATE__;
diff --git a/pd/src/s_midi_alsa.c b/pd/src/s_midi_alsa.c
index 6e9143b3..1d19c111 100644
--- a/pd/src/s_midi_alsa.c
+++ b/pd/src/s_midi_alsa.c
@@ -46,6 +46,7 @@ void sys_alsa_do_open_midi(int nmidiin, int *midiinvec,
int err = 0;
int client;
int i;
+ snd_seq_client_info_t *alsainfo;
alsa_nmidiin = 0;
alsa_nmidiout = 0;
if(nmidiin>MAXMIDIINDEV )
@@ -91,7 +92,6 @@ void sys_alsa_do_open_midi(int nmidiin, int *midiinvec,
}
if (nmidiout == 0 && nmidiin == 0) return;
- snd_seq_client_info_t *alsainfo;
snd_seq_client_info_malloc(&alsainfo);
snd_seq_get_client_info(midi_handle,alsainfo);
snd_seq_client_info_set_name(alsainfo,"Pure Data");
@@ -184,7 +184,7 @@ void sys_alsa_putmidibyte(int portno, int byte)
/* this version uses the asynchronous "read()" ... */
void sys_alsa_poll_midi(void)
{
- char buf[20];
+ unsigned char buf[20];
int count, alsa_source;
int i;
snd_seq_event_t *midievent = NULL;
diff --git a/pd/src/t_tkcmd.c b/pd/src/t_tkcmd.c
index 31c39b52..def4a328 100644
--- a/pd/src/t_tkcmd.c
+++ b/pd/src/t_tkcmd.c
@@ -432,7 +432,7 @@ static void pd_startfromgui( void)
fprintf(debugfd, "%s", cmdbuf);
fflush(debugfd);
#endif
- execl("/bin/sh", "sh", "-c", cmdbuf, 0);
+ execl("/bin/sh", "sh", "-c", cmdbuf, (char*)0);
perror("pd: exec");
_exit(1);
}
diff --git a/pd/src/u_main.tk b/pd/src/u_main.tk
index 26545f98..f0403967 100644
--- a/pd/src/u_main.tk
+++ b/pd/src/u_main.tk
@@ -42,8 +42,8 @@ if {$pd_nt == 1} {
}
if {$pd_nt == 2} {
-# turn on James Tittle II's fast drawing (wait until I can test this...):
-# set tk::mac::useCGDrawing 1
+# turn on James Tittle II's fast drawing
+ set tk::mac::useCGDrawing 1
# set minimum line size for anti-aliasing. If set to 1 or 0, then every
# line will be anti-aliased. While this makes connections and circles in
# [bng] and such look really good, it makes boxes and messages look out of
@@ -56,18 +56,26 @@ if {$pd_nt == 2} {
set pd_guidir $pd_gui2/..
load $pd_guidir/bin/libPdTcl.dylib
set pd_tearoff 0
-
- # tk::mac::OpenDocument is called with the filenames put into the
- # var args whenever docs are either dropped on the Pd.app icon or
- # opened from the Finder.
- # It uses menu_doc_open so it can handles numerous file types.
- proc tk::mac::OpenDocument {args} {
- foreach file $args {
- pd [concat pd open [pdtk_enquote [file tail $file]] \
- [pdtk_enquote [file dirname $file]] \;]
- menu_doc_open [file dirname $file] [file tail $file]
- }
- }
+ global pd_macready
+ set pd_macready 0
+ global pd_macdropped
+ set pd_macdropped ""
+ # tk::mac::OpenDocument is called with the filenames put into the
+ # var args whenever docs are either dropped on the Pd.app icon or
+ # opened from the Finder.
+ # It uses menu_doc_open so it can handles numerous file types.
+ proc tk::mac::OpenDocument {args} {
+ global pd_macready pd_macdropped
+ foreach file $args {
+ if {$pd_macready != 0} {
+ pd [concat pd open [pdtk_enquote [file tail $file]] \
+ [pdtk_enquote [file dirname $file]] \;]
+ menu_doc_open [file dirname $file] [file tail $file]
+ } else {
+ set pd_macdropped $args
+ }
+ }
+ }
}
# hack so you can easily test-run this script in linux... define pd_guidir
@@ -233,11 +241,11 @@ proc pdtk_ping {} {
pd [concat pd ping \;]
}
-proc pdtk_check {x message} {
- set answer [tk_messageBox \-message $x \-type yesno \-icon question]
- switch $answer {
- yes {pd $message} }
-# no {tk_messageBox \-message "cancelled" \-type ok}
+##### routine to ask user if OK and, if so, send a message on to Pd ######
+proc pdtk_check {x message default} {
+ set answer [tk_messageBox \-message $x \-type yesno -default $default \
+ \-icon question]
+ if {$answer == yes} {pd $message}
}
set menu_windowlist {}
@@ -327,7 +335,7 @@ proc menu_send {} {
################## the "Quit" menu command #########################
proc menu_really_quit {} {pd {pd quit;}}
-proc menu_quit {} {pdtk_check {Really quit?} {pd quit;}}
+proc menu_quit {} {pd {pd verifyquit;}}
######### the "Pd" menu command, which puts the Pd window on top ########
proc menu_pop_pd {} {raise .}
@@ -569,7 +577,12 @@ proc menu_print {name} {
proc menu_close {name} {
pdtk_canvas_checkgeometry $name
- pd [concat $name menuclose \;]
+ pd [concat $name menuclose 0 \;]
+}
+
+proc menu_really_close {name} {
+ pdtk_canvas_checkgeometry $name
+ pd [concat $name menuclose 1 \;]
}
proc menu_undo {name} {
@@ -1553,6 +1566,7 @@ proc pdtk_canvas_ctrlkey {name key shift} {
if {$key == "period"} {menu_audio 0}
if {$shift == 1} {
if {$key == "q" || $key == "Q"} {menu_really_quit}
+ if {$key == "w" || $key == "W"} {menu_really_close $topname}
if {$key == "s" || $key == "S"} {menu_saveas $topname}
if {$key == "z" || $key == "Z"} {menu_redo $topname}
if {$key == "b" || $key == "B"} {menu_bng $topname 1}
@@ -3266,6 +3280,16 @@ proc pdtk_pd_startup {version apilist midiapilist fontname} {
# so that we'd know the value of "apilist".
menu_addstd .mbar
+ global pd_nt
+ if {$pd_nt == 2} {
+ global pd_macdropped pd_macready
+ set pd_macready 1
+ foreach file $pd_macdropped {
+ pd [concat pd open [pdtk_enquote [file tail $file]] \
+ [pdtk_enquote [file dirname $file]] \;]
+ menu_doc_open [file dirname $file] [file tail $file]
+ }
+ }
}
##################### DSP ON/OFF, METERS, DIO ERROR ###################
@@ -4186,3 +4210,4 @@ proc pdtk_startup_dialog {id nort flags} {
focus $id.f0
}
+
diff --git a/pd/src/x_list.c b/pd/src/x_list.c
index a08fe193..16de0286 100644
--- a/pd/src/x_list.c
+++ b/pd/src/x_list.c
@@ -4,7 +4,12 @@
#include "m_pd.h"
/* #include <string.h> */
+#ifdef MSW
+#include <malloc.h>
+#else
#include <alloca.h>
+#endif
+
extern t_pd *newest;
#define HAVE_ALLOCA 1 /* LATER this should be set by configure script! */