diff --git a/pd/src/g_array.c b/pd/src/g_array.c index 3005307041407651d82249f5458247fb2155d8d0..3c06df4213fcf2522d99111c223cfc8017e7e0f5 100644 --- a/pd/src/g_array.c +++ b/pd/src/g_array.c @@ -9,6 +9,8 @@ #include "g_canvas.h" #include <math.h> +extern int glob_lmclick; + /* jsarlo { */ #define ARRAYPAGESIZE 1000 /* this should match the page size in u_main.tk */ /* } jsarlo */ @@ -134,10 +136,13 @@ struct _garray t_symbol *x_realname; /* expanded name (symbol we're bound to) */ char x_usedindsp; /* true if some DSP routine is using this */ char x_saveit; /* true if we should save this with parent */ + char x_joc; /* true if we should "jump on click" in a graph */ char x_listviewing; /* true if list view window is open */ char x_hidename; /* don't print name above graph */ - int x_style; /* so much simpler to keep it here */ - t_symbol *x_send; /* send_changed hook */ + int x_style; /* so much simpler to keep it here */ + t_symbol *x_send; /* send_changed hook */ + t_symbol *x_fillcolor; /* color for filled area of the are */ + t_symbol *x_outlinecolor; /* color of the outline around the element */ }; t_pd *garray_arraytemplatecanvas; @@ -145,8 +150,8 @@ t_pd *garray_floattemplatecanvas; static char garray_arraytemplatefile[] = "\ #N canvas 0 0 458 153 10;\n\ #X obj 43 31 struct _float_array array z float float style\n\ -float linewidth float color;\n\ -#X obj 43 70 plot z color linewidth 0 0 1 style;\n\ +float linewidth float color symbol fillcolor symbol outlinecolor;\n\ +#X obj 43 70 plot z color linewidth 0 0 1 style fillcolor outlinecolor;\n\ "; static char garray_floattemplatefile[] = "\ #N canvas 0 0 458 153 10;\n\ @@ -185,7 +190,7 @@ always called by graph_array() below; but when we make a more general way to save and create arrays this might get called more directly. */ static t_garray *graph_scalar(t_glist *gl, t_symbol *s, t_symbol *templatesym, - int saveit) + t_symbol *fill, t_symbol *outline, int saveit) { int i, zz; t_garray *x; @@ -193,8 +198,8 @@ static t_garray *graph_scalar(t_glist *gl, t_symbol *s, t_symbol *templatesym, t_template *template; char *str; t_gpointer gp; - if (!template_findbyname(templatesym)) - return (0); + if (!(template = template_findbyname(templatesym))) + return (0); x = (t_garray *)pd_new(garray_class); x->x_scalar = scalar_new(gl, templatesym); x->x_name = s; @@ -203,6 +208,10 @@ static t_garray *graph_scalar(t_glist *gl, t_symbol *s, t_symbol *templatesym, x->x_usedindsp = 0; x->x_saveit = saveit; x->x_listviewing = 0; + template_setsymbol(template, gensym("fillcolor"), x->x_scalar->sc_vec, + fill, 1); + template_setsymbol(template, gensym("outlinecolor"), x->x_scalar->sc_vec, + outline, 1); glist_add(gl, &x->x_gobj); x->x_glist = gl; char buf[MAXPDSTRING]; @@ -262,6 +271,12 @@ int garray_getname(t_garray *x, t_symbol **namep) return (x->x_hidename); } + /* find out if array elements should "jump on click" in a graph */ +int garray_joc(t_garray *x) +{ + return (x->x_joc); +} + /* if there is one garray in a graph, reset the graph's coordinates to fit a new size and style for the garray */ void garray_fittograph(t_garray *x, int n) @@ -273,7 +288,8 @@ void garray_fittograph(t_garray *x, int n) { vmess(&gl->gl_pd, gensym("bounds"), "ffff", 0., gl->gl_y1, (double) - (x->x_style == PLOTSTYLE_POINTS || n == 1 ? n : n-1), + (x->x_style == PLOTSTYLE_POINTS || x->x_style == PLOTSTYLE_BARS + || n == 1 ? n : n-1), gl->gl_y2); /* close any dialogs that might have the wrong info now... */ gfxstub_deleteforkey(gl); @@ -286,10 +302,23 @@ an appropriate template; then set size and flags. This is called from the menu and in the file format for patches. LATER replace this by a more coherent (and general) invocation. */ -t_garray *graph_array(t_glist *gl, t_symbol *s, t_symbol *templateargsym, - t_floatarg fsize, t_floatarg fflags) +t_garray *graph_array(t_glist *gl, t_symbol *s, int argc, t_atom *argv) { - int n = fsize, i, zz, nwords, zonset, ztype, saveit; + t_symbol *fill; + t_symbol *outline; + int fflags; + + if (argc < 3) {pd_error(gl, "garray: not enough args"); return 0;} + t_symbol *name = atom_getsymbolarg(0, argc--, argv++); + int fsize = (int)atom_getfloatarg(0, argc--, argv++); + t_symbol *templateargsym = atom_getsymbolarg(0, argc--, argv++); + if (argc) fflags = (int)atom_getfloatarg(0, argc--, argv++); + else fflags = 0; + if (argc) fill = atom_getsymbolarg(0, argc--, argv++); + else fill = gensym("black"); + if (argc) outline = atom_getsymbolarg(0, argc--, argv++); + else outline = gensym("black"); + int n = fsize, i, zz, nwords, zonset, ztype, saveit, joc; t_symbol *zarraytype; t_garray *x; t_pd *x2; @@ -332,9 +361,12 @@ t_garray *graph_array(t_glist *gl, t_symbol *s, t_symbol *templateargsym, return (0); } saveit = ((flags & 1) != 0); - x = graph_scalar(gl, s, templatesym, saveit); + x = graph_scalar(gl, name, templatesym, fill, outline, saveit); x->x_hidename = ((flags & 8) >> 3); - x->x_style = style; + x->x_joc = ((flags & 16) >> 4); + x->x_fillcolor = fill; + x->x_outlinecolor = outline; + x->x_style = style; if (n <= 0) n = 100; @@ -344,11 +376,19 @@ t_garray *graph_array(t_glist *gl, t_symbol *s, t_symbol *templateargsym, x->x_style, 1); template_setfloat(template, gensym("linewidth"), x->x_scalar->sc_vec, ((x->x_style == PLOTSTYLE_POINTS) ? 2 : 1), 1); + template_setsymbol(template, gensym("fillcolor"), x->x_scalar->sc_vec, + fill, 1); + template_setsymbol(template, gensym("outlinecolor"), x->x_scalar->sc_vec, + outline, 1); if (x2 = pd_findbyclass(gensym("#A"), garray_class)) pd_unbind(x2, gensym("#A")); - pd_bind(&x->x_gobj.g_pd, gensym("#A")); garray_redraw(x); + +/* todo: need to test to see if this is necessary + doesn't seem like it is... + garray_fittograph(x, n); +*/ return (x); } @@ -358,7 +398,8 @@ void canvas_menuarray(t_glist *canvas) t_glist *x = (t_glist *)canvas; pd_vmess(&x->gl_pd, gensym("editmode"), "i", 1); char cmdbuf[200]; - sprintf(cmdbuf, "pdtk_array_dialog %%s array%d 100 3 1 .x%lx\n", gcount+1, (long unsigned int)canvas); + sprintf(cmdbuf, "pdtk_array_dialog %%s array%d 100 3 1 .x%lx black black\n", + ++gcount, (long unsigned int)canvas); gfxstub_new(&x->gl_pd, x, cmdbuf); } @@ -368,7 +409,6 @@ void garray_properties(t_garray *x, t_glist *canvas) char cmdbuf[200]; t_array *a = garray_getarray(x); t_scalar *sc = x->x_scalar; - if (!a) return; gfxstub_deleteforkey(x); @@ -376,11 +416,11 @@ void garray_properties(t_garray *x, t_glist *canvas) properly; right now we just detect a leading '$' and escape it. There should be a systematic way of doing this. */ sprintf(cmdbuf, ((x->x_name->s_name[0] == '$') ? - "pdtk_array_dialog %%s \\%s %d %d 0 .x%lx\n" : - "pdtk_array_dialog %%s %s %d %d 0 .x%lx\n"), - x->x_name->s_name, a->a_n, x->x_saveit + - 2 * (int)(template_getfloat(template_findbyname(sc->sc_template), - gensym("style"), x->x_scalar->sc_vec, 1)), (long unsigned int)glist_getcanvas(canvas)); + "pdtk_array_dialog %%s \\%s %d %d 0 .x%lx %s %s\n" : + "pdtk_array_dialog %%s %s %d %d 0 .x%lx %s %s\n"), x->x_name->s_name, + a->a_n, x->x_saveit + 2 * x->x_style + 8 * x->x_hidename + + 16 * x->x_joc, (long unsigned int)glist_getcanvas(canvas), + x->x_fillcolor->s_name, x->x_outlinecolor->s_name); gfxstub_new(&x->x_gobj.g_pd, x, cmdbuf); } @@ -389,13 +429,18 @@ void garray_properties(t_garray *x, t_glist *canvas) void glist_arraydialog(t_glist *parent, t_symbol *s, int argc, t_atom *argv) //t_floatarg size, t_floatarg fflags, t_floatarg otherflag, float xdraw, float ydraw) { - t_float size, fflags, otherflag, xdraw, ydraw; - t_symbol *name = atom_getsymbolarg(0, argc, argv); - size = atom_getfloatarg(1, argc, argv); - fflags = atom_getfloatarg(2, argc, argv); - otherflag = atom_getfloatarg(3, argc, argv); - xdraw = atom_getfloatarg(4, argc, argv); - ydraw = atom_getfloatarg(5, argc, argv); + t_atom at[6]; + if (argc !=8) {pd_error(parent, + "arraydialog: wrong number of args"); return;} + t_float size, fflags, otherflag, xdraw, ydraw; + t_symbol *name = atom_getsymbolarg(0, argc, argv); + size = atom_getfloatarg(1, argc, argv); + fflags = atom_getfloatarg(2, argc, argv); + otherflag = atom_getfloatarg(3, argc, argv); + xdraw = atom_getfloatarg(4, argc, argv); + ydraw = atom_getfloatarg(5, argc, argv); + t_symbol *fillcolor = atom_getsymbolarg(6, argc, argv); + t_symbol *outlinecolor = atom_getsymbolarg(7, argc, argv); t_glist *gl; t_garray *a; @@ -407,8 +452,23 @@ void glist_arraydialog(t_glist *parent, t_symbol *s, int argc, t_atom *argv) (size > 1 ? size-1 : size), -1, xdraw+30, ydraw+30, xdraw+30+GLIST_DEFGRAPHWIDTH, ydraw+30+GLIST_DEFGRAPHHEIGHT); gl->gl_hidetext = 1; } - a = graph_array(gl, sharptodollar(name), &s_float, size, flags); + //a = graph_array(gl, sharptodollar(name), &s_float, size, flags); + SETSYMBOL(at, sharptodollar(name)); + SETFLOAT(at+1, size); + SETSYMBOL(at+2, &s_float); + SETFLOAT(at+3, flags); + + /* no idea what xdraw and ydraw are used for... + graph_array doesn't seem to use them + SETFLOAT(at+4, xdraw); + SETFLOAT(at+5, ydraw); + */ + + SETSYMBOL(at+4, fillcolor); + SETSYMBOL(at+5, outlinecolor); + a = graph_array(gl, gensym("array"), 8, at); canvas_dirty(parent, 1); + //canvas_redraw(glist_getcanvas(parent)); garray_fittograph(a, (int)size); sys_vgui("pdtk_canvas_getscroll .x%lx.c\n", (long unsigned int)glist_getcanvas(parent)); @@ -417,32 +477,46 @@ void glist_arraydialog(t_glist *parent, t_symbol *s, int argc, t_atom *argv) extern void canvas_apply_setundo(t_canvas *x, t_gobj *y); /* this is called from the properties dialog window for an existing array */ -void garray_arraydialog(t_garray *x, t_symbol *name, t_floatarg fsize, - t_floatarg fflags, t_floatarg deleteit) +void garray_arraydialog(t_garray *x, t_symbol *s, int argc, t_atom *argv) { - //fprintf(stderr,"================garray_arraydialog\n"); + //fprintf(stderr,"================garray_arraydialog\n"); + + int deleteit = atom_getfloatarg(3, argc, argv); if (deleteit != 0) { - //fprintf(stderr,"deleteit\n"); - //glist_select(x->x_glist, &x->x_gobj); - //canvas_undo_add(x->x_glist, 3, "delete", canvas_undo_set_cut(x->x_glist, 2)); // 2 = UCUT_CLEAR (from g_editor.c) - //currently cannot be undo'd until we do a new kind of undo - int dspwas = canvas_suspend_dsp(); + //fprintf(stderr,"deleteit\n"); + //glist_select(x->x_glist, &x->x_gobj); + //canvas_undo_add(x->x_glist, 3, "delete", canvas_undo_set_cut(x->x_glist, 2)); // 2 = UCUT_CLEAR (from g_editor.c) + //currently cannot be undo'd until we do a new kind of undo + int dspwas = canvas_suspend_dsp(); glist_delete(x->x_glist, &x->x_gobj); - canvas_resume_dsp(dspwas); - canvas_redraw(glist_getcanvas(x->x_glist)); + canvas_resume_dsp(dspwas); + canvas_redraw(glist_getcanvas(x->x_glist)); } - else - { - //need a new kind of undo - //canvas_apply_setundo(glist_getcanvas(x->x_glist), (t_gobj *)x); - - int flags = fflags; - int saveit = ((flags & 1) != 0); - int style = ((flags & 6) >> 1); - /*t_float stylewas = template_getfloat( - template_findbyname(x->x_scalar->sc_template), - gensym("style"), x->x_scalar->sc_vec, 1);*/ + else + { + //need a new kind of undo + //canvas_apply_setundo(glist_getcanvas(x->x_glist), (t_gobj *)x); + + if (argc !=8) + { + pd_error(x, "arraydialog: wrong number of args"); return; + } + t_symbol *name = atom_getsymbolarg(0, argc, argv); + int fsize = atom_getfloatarg(1, argc, argv); + int flags = atom_getfloatarg(2, argc, argv); + t_symbol *fill = atom_getsymbolarg(6, argc, argv); + t_symbol *outline = atom_getsymbolarg(7, argc, argv); + int saveit = ((flags & 1) != 0); + int style = ((flags & 6) >> 1); + /* todo: revisit this filestyle business + if (style < 2) style = !style; + */ + int hidename = ((flags & 8) >> 3); + int joc = ((flags & 16) >> 4); + /*t_float stylewas = template_getfloat( + template_findbyname(x->x_scalar->sc_template), + gensym("style"), x->x_scalar->sc_vec, 1);*/ int size; int styleonset, styletype; t_symbol *stylearraytype; @@ -484,21 +558,30 @@ void garray_arraydialog(t_garray *x, t_symbol *name, t_floatarg fsize, if (size != a->a_n) garray_resize(x, size); if (style != x->x_style) { - x->x_style = style; + x->x_style = style; garray_fittograph(x, size); - } - //fprintf(stderr,"style=%d %f\n", style, (t_float)x->x_style); + } + //fprintf(stderr,"style=%d %f\n", style, (t_float)x->x_style); template_setfloat(scalartemplate, gensym("style"), x->x_scalar->sc_vec, (t_float)x->x_style, 0); template_setfloat(scalartemplate, gensym("linewidth"), - x->x_scalar->sc_vec, ((x->x_style == PLOTSTYLE_POINTS) ? 2 : 1), 1); + x->x_scalar->sc_vec, ((x->x_style == PLOTSTYLE_POINTS) ? 2 : 1), 1); + template_setsymbol(scalartemplate, gensym("fillcolor"), + x->x_scalar->sc_vec, fill, 0); + template_setsymbol(scalartemplate, gensym("outlinecolor"), + x->x_scalar->sc_vec, outline, 0); - char buf[MAXPDSTRING]; - sprintf(buf, "%s_changed", x->x_realname->s_name); - x->x_send = gensym(buf); + char buf[MAXPDSTRING]; + sprintf(buf, "%s_changed", x->x_realname->s_name); + x->x_send = gensym(buf); garray_setsaveit(x, (saveit != 0)); - //fprintf(stderr,"GARRAY_REDRAW\n"); + x->x_joc = joc; + x->x_hidename = hidename; + x->x_fillcolor = fill; + x->x_outlinecolor = outline; + x->x_style = style; + //fprintf(stderr,"GARRAY_REDRAW\n"); garray_redraw(x); canvas_dirty(x->x_glist, 1); } @@ -656,6 +739,7 @@ void array_getcoordinate(t_glist *glist, *wp = wpix; } +extern int array_joc; /* from g_canvas.h */ static t_float array_motion_xcumulative; static t_float array_motion_ycumulative; static t_fielddesc *array_motion_xfield; @@ -780,7 +864,6 @@ int scalar_doclick(t_word *data, t_template *template, t_scalar *sc, t_array *ap, struct _glist *owner, t_float xloc, t_float yloc, int xpix, int ypix, int shift, int alt, int dbl, int doit); - /* try clicking on an element of the array as a scalar (if clicking on the trace of the array failed) */ static int array_doclick_element(t_array *array, t_glist *glist, @@ -834,7 +917,7 @@ int array_doclick(t_array *array, t_glist *glist, t_scalar *sc, t_array *ap, t_fielddesc *xfield, t_fielddesc *yfield, t_fielddesc *wfield, int xpix, int ypix, int shift, int alt, int dbl, int doit) { - //fprintf(stderr,"array_doclick %d\n", doit); + //fprintf(stderr,"array_doclick %d\n", doit); t_canvas *elemtemplatecanvas; t_template *elemtemplate; int elemsize, yonset, wonset, xonset, i; @@ -855,9 +938,12 @@ int array_doclick(t_array *array, t_glist *glist, t_scalar *sc, t_array *ap, //fprintf(stderr," array_getcoordinate %d: pxpix:%f pypix:%f pwpix:%f dx:%f dy:%f elemsize:%d yonset:%d wonset:%d xonset:%d xloc:%f yloc:%f xinc:%f\n", i, pxpix, pypix, pwpix, dx, dy, elemsize, yonset, wonset, xonset, xloc, yloc, xinc); if (pwpix < 4) pwpix = 4; - if (xpix >= pxpix1 && xpix <= pxpix2 && ypix >= pypix-pwpix && ypix <= pypix+pwpix) { - best = i; - break; + if (xpix >= (int)pxpix1 && xpix <= (int)pxpix2 && + ((array_joc) || + (ypix >= pypix-pwpix && ypix <= pypix+pwpix))) + { + best = i; + break; } /* if (pwpix < 4) @@ -884,7 +970,7 @@ int array_doclick(t_array *array, t_glist *glist, t_scalar *sc, t_array *ap, //fprintf(stderr," 1st %f %f %f %f %f %d %d %d %d %d\n", pxpix, pypix, pwpix, dx, dy, elemsize, yonset, wonset, xonset, i);*/ } //fprintf(stderr," best = %f\n", best); - if (best == -1) //this is the arbitrary radius away from the actual object's center, originally 8 + if (best == -1 && (array_joc == 0)) //this is the arbitrary radius away from the actual object's center, originally 8 { //fprintf(stderr," best > 8\n"); if (scalarvis != 0) { @@ -923,6 +1009,20 @@ int array_doclick(t_array *array, t_glist *glist, t_scalar *sc, t_array *ap, //if (dx + dy <= best || dx + dy2 <= best || dx + dy3 <= best) //{ //fprintf(stderr, "dy=%f dy2=%f dy3=%f\n", dy, dy2, dy3); + +/* from array-rev */ + + int hit = 0; + if(array_joc) + { + hit = (xpix >= pxpix1) && (xpix < pxpix2); + } + else + hit = dx + dy <= best || dx + dy2 <= best || dx + dy3 <= best; + + +/* end array-rev */ + if (dy < dy2 && dy < dy3) { array_motion_fatten = 0; //fprintf(stderr,"A\n"); @@ -931,11 +1031,11 @@ int array_doclick(t_array *array, t_glist *glist, t_scalar *sc, t_array *ap, array_motion_fatten = -1; //fprintf(stderr,"B\n"); } - else { + else if (!array_joc) { array_motion_fatten = 1; //fprintf(stderr,"C\n"); } - if (doit) + if (doit || (glob_lmclick && array_joc)) { char *elem = (char *)array->a_vec; array_motion_elemsize = elemsize; @@ -1003,10 +1103,12 @@ int array_doclick(t_array *array, t_glist *glist, t_scalar *sc, t_array *ap, else if (yonset >= 0) { array_motion_yfield = yfield; - array_motion_ycumulative = + array_motion_ycumulative = fielddesc_getcoord(yfield, array_motion_template, (t_word *)(elem + i * elemsize), 1); /* *(t_float *)((elem + elemsize * i) + yonset); */ + if (array_joc) + array_motion(0, 0, ypix - pypix); } else { @@ -1148,9 +1250,11 @@ static void garray_save(t_gobj *z, t_binbuf *b) x->x_scalar->sc_vec, 0); */ filestyle = (x->x_style == PLOTSTYLE_POINTS ? 0 : (x->x_style == PLOTSTYLE_POLY ? 1 : x->x_style)); - binbuf_addv(b, "sssisi;", gensym("#X"), gensym("array"), + + binbuf_addv(b, "sssisiss;", gensym("#X"), gensym("array"), x->x_name, array->a_n, &s_float, - x->x_saveit + 2 * filestyle + 8*x->x_hidename); + x->x_saveit + 2 * filestyle + 8*x->x_hidename + + 16 * x->x_joc, x->x_fillcolor, x->x_outlinecolor); if (x->x_saveit) { int n = array->a_n, n2 = 0; @@ -1325,7 +1429,7 @@ static void garray_dofo(t_garray *x, int npoints, t_float dcval, if (npoints == 0) npoints = 512; /* dunno what a good default would be... */ if (npoints != (1 << ilog2(npoints))) - post("%s: rounnding to %d points", array->a_templatesym->s_name, + post("%s: rounding to %d points", array->a_templatesym->s_name, (npoints = (1<<ilog2(npoints)))); garray_resize(x, npoints + 3); phaseincr = 2. * 3.14159 / npoints; @@ -1648,7 +1752,7 @@ void g_array_setup(void) class_addmethod(garray_class, (t_method)garray_normalize, gensym("normalize"), A_DEFFLOAT, 0); class_addmethod(garray_class, (t_method)garray_arraydialog, - gensym("arraydialog"), A_SYMBOL, A_FLOAT, A_FLOAT, A_FLOAT, A_NULL); + gensym("arraydialog"), A_GIMME, 0); /* jsarlo { */ class_addmethod(garray_class, (t_method)garray_arrayviewlist_new, gensym("arrayviewlistnew"), A_NULL); diff --git a/pd/src/g_canvas.c b/pd/src/g_canvas.c index 15809adbc85a2336c4af4bc5b967e4cf6e7e841a..4a8f9790bfe624de3b6470e871c88ce63551036c 100644 --- a/pd/src/g_canvas.c +++ b/pd/src/g_canvas.c @@ -1331,6 +1331,7 @@ static int tabcount = 0; static void *table_new(t_symbol *s, t_floatarg f) { t_atom a[9]; + t_atom ga[4]; t_glist *gl; t_canvas *x, *z = canvas_getcurrent(); if (s == &s_) @@ -1356,7 +1357,11 @@ static void *table_new(t_symbol *s, t_floatarg f) gl = glist_addglist((t_glist*)x, &s_, 0, -1, (f > 1 ? f-1 : 1), 1, 50, 350, 550, 50); - graph_array(gl, s, &s_float, f, 0); + SETSYMBOL(ga, s); + SETFLOAT(ga+1, f); + SETSYMBOL(ga+2, &s_float); + SETFLOAT(ga+3, 0); + graph_array(gl, gensym("array"), 4, ga); canvas_pop(x, 0); diff --git a/pd/src/g_canvas.h b/pd/src/g_canvas.h index 449edbf5c7dc2392ce679fd0581e3f0da665bd8d..fa7b9d56f05314287af040b01a8be89f2330b732 100644 --- a/pd/src/g_canvas.h +++ b/pd/src/g_canvas.h @@ -403,6 +403,7 @@ extern int glist_valid; /* incremented when pointers might be stale */ #define PLOTSTYLE_POINTS 0 /* plotting styles for arrays */ #define PLOTSTYLE_POLY 1 #define PLOTSTYLE_BEZ 2 +#define PLOTSTYLE_BARS 3 /* ------------------- functions on any gobj ----------------------------- */ EXTERN void gobj_getrect(t_gobj *x, t_glist *owner, int *x1, int *y1, @@ -457,7 +458,8 @@ EXTERN void glist_glist(t_glist *g, t_symbol *s, int argc, t_atom *argv); EXTERN t_glist *glist_addglist(t_glist *g, t_symbol *sym, t_float x1, t_float y1, t_float x2, t_float y2, t_float px1, t_float py1, t_float px2, t_float py2); -EXTERN void glist_arraydialog(t_glist *parent, t_symbol *s, int argc, t_atom *argv); +EXTERN void glist_arraydialog(t_glist *parent, t_symbol *s, + int argc, t_atom *argv); EXTERN t_binbuf *glist_writetobinbuf(t_glist *x, int wholething); EXTERN int glist_isgraph(t_glist *x); EXTERN void glist_redraw(t_glist *x); @@ -600,11 +602,11 @@ EXTERN void linetraverser_skipobject(t_linetraverser *t); EXTERN t_template *garray_template(t_garray *x); /* -------------------- arrays --------------------- */ -EXTERN t_garray *graph_array(t_glist *gl, t_symbol *s, t_symbol *tmpl, - t_floatarg f, t_floatarg saveit); +EXTERN t_garray *graph_array(t_glist *gl, t_symbol *s, int argc, t_atom *argv); EXTERN t_array *array_new(t_symbol *templatesym, t_gpointer *parent); EXTERN void array_resize(t_array *x, int n); EXTERN void array_free(t_array *x); +int array_joc; /* for "jump on click" array inside a graph */ /* --------------------- gpointers and stubs ---------------- */ EXTERN t_gstub *gstub_new(t_glist *gl, t_array *a); diff --git a/pd/src/g_graph.c b/pd/src/g_graph.c index 598a045a5a5aa75464772f3422c6c546c89a67f8..b562f34dfdf973dd02c0fd24e768b0ac0f41569a 100644 --- a/pd/src/g_graph.c +++ b/pd/src/g_graph.c @@ -16,10 +16,13 @@ to this file... */ #include <stdio.h> #include <string.h> +extern int array_joc; +int garray_joc(t_garray *x); + /* ---------------------- forward definitions ----------------- */ static void graph_vis(t_gobj *gr, t_glist *unused_glist, int vis); -static void graph_graphrect(t_gobj *z, t_glist *glist, +void graph_graphrect(t_gobj *z, t_glist *glist, int *xp1, int *yp1, int *xp2, int *yp2); static void graph_getrect(t_gobj *z, t_glist *glist, int *xp1, int *yp1, int *xp2, int *yp2); @@ -857,7 +860,7 @@ static void graph_vis(t_gobj *gr, t_glist *parent_glist, int vis) { //i++; sys_vgui(".x%lx.c create text %d %d -text {%s} -anchor nw\ - -font {{%s} %d %s} -tags {%s label graph} -fill %s\n", + -font {{%s} -%d %s} -tags {%s label graph} -fill %s\n", (long)glist_getcanvas(x), x1+2, i, arrayname->s_name, sys_font, sys_hostfontsize(glist_getfont(x)), sys_fontweight, tag, (glist_isselected(x, gr) ? "$pd_colors(selection)" : "$pd_colors(graph_border)")); @@ -987,7 +990,7 @@ static void graph_vis(t_gobj *gr, t_glist *parent_glist, int vis) /* get the graph's rectangle, not counting extra swelling for controls to keep them inside the graph. This is the "logical" pixel size. */ -static void graph_graphrect(t_gobj *z, t_glist *glist, +void graph_graphrect(t_gobj *z, t_glist *glist, int *xp1, int *yp1, int *xp2, int *yp2) { t_glist *x = (t_glist *)z; @@ -1339,11 +1342,18 @@ static int graph_click(t_gobj *z, struct _glist *glist, return (0); else { - int x1, y1, x2, y2; for (y = x->gl_list; y; y = y->g_next) { + if(pd_class(&y->g_pd) == garray_class && + !y->g_next && + (array_joc = garray_joc((t_garray *)y)) && + (clickreturned = gobj_click(y, x, xpix, ypix, shift, alt, 0, doit))) + break; + else + { + int x1, y1, x2, y2; /* check if the object wants to be clicked */ - if (canvas_hitbox(x, y, xpix, ypix, &x1, &y1, &x2, &y2)) { + if (canvas_hitbox(x, y, xpix, ypix, &x1, &y1, &x2, &y2)) clickme = y; //fprintf(stderr," found clickable %d\n", clickreturned); } @@ -1409,7 +1419,7 @@ void g_graph_setup(void) class_addmethod(canvas_class, (t_method)graph_ylabel, gensym("ylabel"), A_GIMME, 0); class_addmethod(canvas_class, (t_method)graph_array, gensym("array"), - A_SYMBOL, A_FLOAT, A_SYMBOL, A_DEFFLOAT, A_NULL); + A_GIMME, A_NULL); class_addmethod(canvas_class, (t_method)canvas_menuarray, gensym("menuarray"), A_NULL); class_addmethod(canvas_class, (t_method)glist_sort, diff --git a/pd/src/g_template.c b/pd/src/g_template.c index 70446f764a03a65b125198604a3f5ddab0f6e6bf..43c83da44d1c8c6e8b7ff84043afb3bdd1a0655f 100644 --- a/pd/src/g_template.c +++ b/pd/src/g_template.c @@ -11,7 +11,8 @@ #include "g_canvas.h" void array_redraw(t_array *a, t_glist *glist); - +void graph_graphrect(t_gobj *z, t_glist *glist, + int *xp1, int *yp1, int *xp2, int *yp2); /* This file contains text objects you would put in a canvas to define a template. Templates describe objects of type "array" (g_array.c) and @@ -1447,6 +1448,8 @@ typedef struct _plot t_fielddesc x_wpoints; t_fielddesc x_vis; /* visible */ t_fielddesc x_scalarvis; /* true if drawing the scalar at each point */ + t_fielddesc x_symoutlinecolor; /* color as hex symbol */ + t_fielddesc x_symfillcolor; /* fill color as hex symbol */ } t_plot; static void *plot_new(t_symbol *classsym, t_int argc, t_atom *argv) @@ -1511,6 +1514,10 @@ static void *plot_new(t_symbol *classsym, t_int argc, t_atom *argv) else fielddesc_setfloat_const(&x->x_xinc, 1); if (argc) fielddesc_setfloatarg(&x->x_style, argc--, argv++); else fielddesc_setfloat_const(&x->x_style, defstyle); + if (argc) fielddesc_setsymbolarg(&x->x_symfillcolor, argc--, argv++); + else argc--, argv++; + if (argc) fielddesc_setsymbolarg(&x->x_symoutlinecolor, argc--, argv++); + return (x); } @@ -1541,7 +1548,8 @@ static int plot_readownertemplate(t_plot *x, t_symbol **elemtemplatesymp, t_array **arrayp, t_float *linewidthp, t_float *xlocp, t_float *xincp, t_float *ylocp, t_float *stylep, t_float *visp, t_float *scalarvisp, - t_fielddesc **xfield, t_fielddesc **yfield, t_fielddesc **wfield) + t_fielddesc **xfield, t_fielddesc **yfield, t_fielddesc **wfield, t_symbol **fillcolorp, + t_symbol **outlinecolorp) { int arrayonset, type; t_symbol *elemtemplatesym; @@ -1577,6 +1585,11 @@ static int plot_readownertemplate(t_plot *x, *xfield = &x->x_xpoints; *yfield = &x->x_ypoints; *wfield = &x->x_wpoints; + *fillcolorp = fielddesc_getsymbol(&x->x_symfillcolor, ownertemplate, + data, 1); + *outlinecolorp = fielddesc_getsymbol(&x->x_symoutlinecolor, ownertemplate, + data, 1); + return (0); } @@ -1648,6 +1661,8 @@ static void plot_getrect(t_gobj *z, t_glist *glist, t_canvas *elemtemplatecanvas; t_template *elemtemplate; t_symbol *elemtemplatesym; + t_symbol *symfillcolor; + t_symbol *symoutlinecolor; t_float linewidth, xloc, xinc, yloc, style, xsum, yval, vis, scalarvis; t_array *array; int x1 = 0x7fffffff, y1 = 0x7fffffff, x2 = -0x7fffffff, y2 = -0x7fffffff; @@ -1663,7 +1678,8 @@ static void plot_getrect(t_gobj *z, t_glist *glist, }*/ if (!plot_readownertemplate(x, data, template, &elemtemplatesym, &array, &linewidth, &xloc, &xinc, &yloc, &style, - &vis, &scalarvis, &xfielddesc, &yfielddesc, &wfielddesc) && + &vis, &scalarvis, &xfielddesc, &yfielddesc, &wfielddesc, + &symfillcolor, &symoutlinecolor) && (vis != 0) && !array_getfields(elemtemplatesym, &elemtemplatecanvas, &elemtemplate, &elemsize, @@ -1781,6 +1797,11 @@ static void plot_vis(t_gobj *z, t_glist *glist, t_scalar *sc, t_symbol *elemtemplatesym; t_float linewidth, xloc, xinc, yloc, style, usexloc, xsum, yval, vis, scalarvis; + t_symbol *symfill; + t_symbol *symoutline; + char outline[20]; + numbertocolor(fielddesc_getfloat(&x->x_outlinecolor, template, + data, 1), outline); t_array *array; int nelem; char *elem; @@ -1796,7 +1817,8 @@ static void plot_vis(t_gobj *z, t_glist *glist, t_scalar *sc, if (plot_readownertemplate(x, data, template, &elemtemplatesym, &array, &linewidth, &xloc, &xinc, &yloc, &style, - &vis, &scalarvis, &xfielddesc, &yfielddesc, &wfielddesc) || + &vis, &scalarvis, &xfielddesc, &yfielddesc, &wfielddesc, &symfill, + &symoutline) || ((vis == 0) && tovis) /* see above for 'tovis' */ || array_getfields(elemtemplatesym, &elemtemplatecanvas, &elemtemplate, &elemsize, xfielddesc, yfielddesc, wfielddesc, @@ -1807,10 +1829,20 @@ static void plot_vis(t_gobj *z, t_glist *glist, t_scalar *sc, if (tovis) { - if (style == PLOTSTYLE_POINTS) + /* check if old 3-digit color field is being used... */ + int dscolor = fielddesc_getfloat(&x->x_outlinecolor, template, data, 1); + if (dscolor != 0) { + char outline[20]; + numbertocolor(dscolor, outline); + symoutline = gensym(outline); + } + if (style == PLOTSTYLE_POINTS || style == PLOTSTYLE_BARS) + { + symfill = style == PLOTSTYLE_POINTS ? symoutline : symfill; t_float minyval = 1e20, maxyval = -1e20; int ndrawn = 0; + sys_vgui(".x%lx.c create path { \\\n", glist_getcanvas(glist)); for (xsum = basex + xloc, i = 0; i < nelem; i++) { t_float yval, xpix, ypix, nextxloc; @@ -1843,44 +1875,79 @@ static void plot_vis(t_gobj *z, t_glist *glist, t_scalar *sc, minyval = yval; if (i == nelem-1 || inextx != ixpix) { - //fprintf(stderr,"%f %f %f %f %f\n", basey, minyval, maxyval,glist->gl_y2,glist->gl_y1); - // with the following experimental code we can prevent drawing outside the gop window (preferred but needs to be further tested) - /*if (glist->gl_y2 > glist->gl_y1) { - if (minyval >= glist->gl_y1 && maxyval <= glist->gl_y2) draw_me = 1; - else draw_me = 0; - } else { - if (minyval >= glist->gl_y2 && maxyval <= glist->gl_y1) draw_me = 1; - else draw_me = 0; - } - if (draw_me) {*/ - //we subtract 1 from y to keep it in sync with the rest of the types of templates - sys_vgui( - ".x%lx.c create prect %d %d %d %d -fill black -strokewidth 0 -tags {.x%lx.x%lx.template%lx scalar%lx}\n", - glist_getcanvas(glist), - ixpix, (int)glist_ytopixels(glist, - basey + fielddesc_cvttocoord(yfielddesc, minyval)) - 1, - inextx, (int)(glist_ytopixels(glist, - basey + fielddesc_cvttocoord(yfielddesc, maxyval)) - + linewidth) - 1, glist_getcanvas(glist), glist, - data, sc); - - //} //part of experimental code above + int py2 = 0; + int border = 0; + if(style == PLOTSTYLE_POINTS) + py2 = (int)(glist_ytopixels(glist, + basey + fielddesc_cvttocoord(yfielddesc, maxyval)) + + linewidth) - 1; + else + { + /* this should probably be changed to anchor to the + y-minimum instead of the bottom of the graph. That + way the user can invert the y min/max to get a graph + anchored from the top */ + + if(glist->gl_isgraph && !glist->gl_havewindow) + { + int x1, y1, x2, y2; + graph_graphrect(&glist->gl_gobj, glist->gl_owner, + &x1, &y1, &x2, &y2); + py2 = y2; + border = 1; + } + } + //fprintf(stderr,"%f %f %f %f %f\n", basey, minyval, maxyval,glist->gl_y2,glist->gl_y1); + // with the following experimental code we can prevent drawing outside the gop window (preferred but needs to be further tested) + /*if (glist->gl_y2 > glist->gl_y1) { + if (minyval >= glist->gl_y1 && maxyval <= glist->gl_y2) draw_me = 1; + else draw_me = 0; + } else { + if (minyval >= glist->gl_y2 && maxyval <= glist->gl_y1) draw_me = 1; + else draw_me = 0; + } + if (draw_me) {*/ + //we subtract 1 from y to keep it in sync with the rest of the types of templates + /* This is the old, inefficient code that creates a separate canvas item for each element... + sys_vgui( + ".x%lx.c create prect %d %d %d %d -fill %s -stroke %s -strokewidth %d -tags {.x%lx.x%lx.template%lx array}\n", + glist_getcanvas(glist), + ixpix, (int)glist_ytopixels(glist, + basey + fielddesc_cvttocoord(yfielddesc, minyval)) - 1, + inextx, py2, symfill->s_name, symoutline->s_name, + border, glist_getcanvas(glist), glist, data); + */ + + /* For efficiency, we make a single path item for the trace or bargraph */ + int mex1 = ixpix; + int mey1 = (int)glist_ytopixels(glist, basey + fielddesc_cvttocoord(yfielddesc, minyval)) - 1; + int mex2 = inextx; + int mey2 = py2; + sys_vgui("M %d %d H %d V %d H %d z\\\n", + mex1, mey1, mex2, mey2, mex1); + //} //part of experimental code above ndrawn++; minyval = 1e20; maxyval = -1e20; } if (ndrawn > 2000 || ixpix >= 3000) break; } + /* end of the path item from above */ + sys_vgui("} -fill %s -stroke %s -strokewidth %d -tags {.x%lx.x%lx.template%lx array}\n", + symfill->s_name, symoutline->s_name, + style == PLOTSTYLE_POINTS ? 0 : 1, + glist_getcanvas(glist), glist, data); + } else { - char outline[20]; + //char outline[20]; int lastpixel = -1, ndrawn = 0; t_float yval = 0, wval = 0, xpix; int ixpix = 0; /* draw the trace */ - numbertocolor(fielddesc_getfloat(&x->x_outlinecolor, template, - data, 1), outline); + //numbertocolor(fielddesc_getfloat(&x->x_outlinecolor, template, + // data, 1), outline); if (wonset >= 0) { /* found "w" field which controls linewidth. The trace is @@ -1953,8 +2020,8 @@ static void plot_vis(t_gobj *z, t_glist *glist, t_scalar *sc, fielddesc_cvttocoord(wfielddesc, wval))); } ouch: - sys_vgui(" -strokewidth 1 -stroke %s\\\n", - outline); + sys_vgui(" -strokewidth 1 -fill %s -stroke %s\\\n", + symfill->s_name, symoutline->s_name); //if (style == PLOTSTYLE_BEZ) sys_vgui("-smooth 1\\\n"); //this doesn't work with tkpath sys_vgui("-tags {.x%lx.x%lx.template%lx scalar%lx}\n", glist_getcanvas(glist), glist, @@ -1997,13 +2064,19 @@ static void plot_vis(t_gobj *z, t_glist *glist, t_scalar *sc, glist_ytopixels(glist, basey + yloc + fielddesc_cvttocoord(yfielddesc, yval))); - sys_vgui("-strokewidth %f\\\n", linewidth); + //sys_vgui("-strokewidth %f\\\n", linewidth); //sys_vgui("-fill %s\\\n", outline); + sys_vgui("-strokewidth %f -stroke %s\\\n", linewidth, symoutline->s_name); + //sys_vgui("-fill %s\\\n", symoutline->s_name); //if (style == PLOTSTYLE_BEZ) sys_vgui("-smooth 1\\\n"); //this doesn't work with tkpath - + sys_vgui("-tags {.x%lx.x%lx.template%lx scalar%lx}\n", glist_getcanvas(glist), glist, data,sc); } } + /* make sure the array drawings are behind the graph */ + sys_vgui(".x%lx.c lower plot%lx graph%lx\n", glist_getcanvas(glist), + data, glist); + /* We're done with the outline; now draw all the points. This code is inefficient since the template has to be searched for drawing instructions for every last point. */ @@ -2079,11 +2152,14 @@ static int plot_click(t_gobj *z, t_glist *glist, t_float linewidth, xloc, xinc, yloc, style, vis, scalarvis; t_array *array; t_fielddesc *xfielddesc, *yfielddesc, *wfielddesc; + t_symbol *symfillcolor; + t_symbol *symoutlinecolor; if (!plot_readownertemplate(x, data, template, &elemtemplatesym, &array, &linewidth, &xloc, &xinc, &yloc, &style, &vis, &scalarvis, - &xfielddesc, &yfielddesc, &wfielddesc) && (vis != 0)) + &xfielddesc, &yfielddesc, &wfielddesc, &symfillcolor, &symoutlinecolor) + && (vis != 0)) { //fprintf(stderr," ->array_doclick\n"); return (array_doclick(array, glist, sc, ap, diff --git a/pd/src/pd.tk b/pd/src/pd.tk index 241b254bc387f8bd64aa59ba73cb517ee8fbd343..e307a8137a42b72f446300edebf15ebe5bdaabd1 100644 --- a/pd/src/pd.tk +++ b/pd/src/pd.tk @@ -6228,31 +6228,43 @@ proc array_apply {id canvas} { global $var_array_saveit set var_array_drawasrects [concat array_drawasrects_$vid] global $var_array_drawasrects + set var_array_joc [concat array_joc_$vid] + global $var_array_joc set var_array_otherflag [concat array_otherflag_$vid] global $var_array_otherflag + set var_array_fill [concat array_fill_$vid] + global $var_array_fill + set var_array_outline [concat array_outline_$vid] + global $var_array_outline + set mofo [eval concat $$var_array_name] if {[string index $mofo 0] == "$"} { set mofo [string replace $mofo 0 0 #] } set saveit [eval concat $$var_array_saveit] set drawasrects [eval concat $$var_array_drawasrects] + set joc [eval concat $$var_array_joc] + set fill [eval concat $$var_array_fill] + set outline [eval concat $$var_array_outline] - #puts stderr "...[expr $saveit + 2 * $drawasrects]" + # puts stderr "...[expr $saveit + 2 * $drawasrects + 16 * $joc]" set xdraw [expr int([$canvas.c canvasx 0])] set ydraw [expr int([$canvas.c canvasy 0])] pd [concat $id arraydialog $mofo \ [eval concat $$var_array_n] \ - [expr $saveit + 2 * $drawasrects] \ + [expr $saveit + 2 * $drawasrects + 16 * $joc] \ [eval concat $$var_array_otherflag] \ $xdraw \ $ydraw \ + $fill $outline \ \;] } # jsarlo -proc array_viewlist {id} { +proc array_viewlist {id arraydialogwindow} { + canvas_cancel $arraydialogwindow pd [concat $id arrayviewlistnew\;] } # end jsarlo @@ -6267,9 +6279,73 @@ proc array_ok {id canvas} { array_cancel $id } -proc pdtk_array_dialog {id name n flags newone canvas} { - set vid [string trimleft $id .] +proc array_choosecolor {widget mytoplevel colorvar} { +# set colorp [format "::pd_array_%scolor(%s)" $type $mytoplevel] +# if {[info exists $colorp]} { +# set initcolor [set $colorp] +# } else { +# set initcolor "black"} + global $colorvar + set tmp [tk_chooseColor -parent $mytoplevel -initialcolor [set $colorvar]] + if {$tmp eq ""} { + return + } else { + set $colorvar $tmp + $widget configure -background $tmp -activebackground $tmp + } +} +proc array_update_drawas {style fillframe outlineframe outlinelabel} { + if {$style == 3} { + $outlinelabel configure -text "outline color" + pack $fillframe -after $outlineframe -side top -anchor w + } else { + pack forget $fillframe + $outlinelabel configure -text "trace color" + } +} + +proc pdtk_array_dialog {gfxstub name n flags newone canvas fill outline} { + # A little complex: + # 1) When an array is created from the "Put" menu, there is + # no associated canvas dialog. The array dialog creates its + # own toplevel. + # 2) When an array is changed from the "Properties" dialog, + # the array dialog is created as a frame in a ttk::notebook + # within the graph's canvas dialog window. The canvas_properties + # method always creates a canvas dialog _before_ any array dialogs, + # so we use a global variable-- ::pd_canvasdialog_current-- to + # give this array dialog a reference to it's parent window. (But + # remember that there can be multiple dialogs open at once, so + # pd_canvasdialog_current is only "fresh" for the duration of this + # proc...) + # + # Variables + # --------- + # $gfxstub - callback address understood by Pd + # to refer to _this_ array + # + # $::pd_canvasdialog_current - as long as this isn't a new array + # (i.e., $newone == 0) this is the + # address of the toplevel that holds + # the ttk::notebook for the array and + # graph dialogs + # + # $vid - $gfxstub without the "." (probably + # should be replaced with tcl arrays) + # $id - abstracted widget parent (may be a + # notebook, toplevel, etc.) + # $mytoplevel - toplevel window for this dialog + # + ################################################################## + + + +if {[catch { + + set vid [string trimleft $gfxstub .] + set var_array_canvas [concat array_canvas_$vid] + global $var_array_canvas set var_array_name [concat array_name_$vid] global $var_array_name set var_array_n [concat array_n_$vid] @@ -6278,29 +6354,91 @@ proc pdtk_array_dialog {id name n flags newone canvas} { global $var_array_saveit set var_array_drawasrects [concat array_drawasrects_$vid] global $var_array_drawasrects + set var_array_joc [concat array_joc_$vid] + global $var_array_joc set var_array_otherflag [concat array_otherflag_$vid] global $var_array_otherflag + set var_array_fill [concat array_fill_$vid] + global $var_array_fill + set var_array_outline [concat array_outline_$vid] + global $var_array_outline + set $var_array_canvas $canvas set $var_array_name $name set $var_array_n $n set $var_array_saveit [expr ( $flags & 1 ) != 0] - set $var_array_drawasrects [expr ( $flags & 2 ) != 0] + set $var_array_drawasrects [expr ( $flags & 6 ) >> 1] + set $var_array_joc [expr ( $flags & 16 ) != 0] set $var_array_otherflag 0 - - toplevel $id -class [winfo class .] - wm title $id {Edit Array} - match_linux_wm [list $id configure] - wm resizable $id 0 0 - global pointer_x_global pointer_y_global - wm geometry $id "+[expr $pointer_x_global+50]+[expr $pointer_y_global-12]" - wm attributes $id -topmost 1 - wm protocol $id WM_DELETE_WINDOW [concat array_cancel $id] + set $var_array_fill $fill + set $var_array_outline $outline + + set multiarray_graph 0 + + set id {} + set mytoplevel {} + + if {$newone} { + set id $gfxstub + set mytoplevel $id + + toplevel $id -class [winfo class .] + wm title $id {New Array} + match_linux_wm [list $id configure] + wm resizable $id 0 0 + global pointer_x_global pointer_y_global + wm geometry $id \ + "+[expr $pointer_x_global+50]+[expr $pointer_y_global-12]" + wm attributes $id -topmost 1 + wm protocol $id WM_DELETE_WINDOW [concat array_cancel $id] + } else { + set id $::pd_canvasdialog_current + # if we're the first array, then get rid of + # stupid options in the graph tab that are of + # no use + if {[$id.n index end] == 1} { + pack forget $id.n.canvasdialog.x.f2.label4 + pack forget $id.n.canvasdialog.x.f2.entry4 + pack forget $id.n.canvasdialog.y.f2.label4 + pack forget $id.n.canvasdialog.y.f2.entry4 + pack configure $id.n.canvasdialog.x.f2.label3 -expand 0 + pack configure $id.n.canvasdialog.x.f2.entry3 -expand 0 + pack configure $id.n.canvasdialog.y.f2.label3 -expand 0 + pack configure $id.n.canvasdialog.y.f2.entry3 -expand 0 + foreach slave [pack slaves $id.n.canvasdialog] { + if {[string match *scale $slave] || + [string match *graphme $slave]} { + pack forget $slave + } + } + } + set mytoplevel $id + set arrayno [$id.n index end] + set multiarray_graph [expr {$arrayno-1 != 0}] + set title [format "Array #%d" $arrayno] + if {$arrayno == 1} { + set title "Array" + } else { + $id.n tab 0 -text "Array #1" + } + $id.n insert \ + [expr {[$id.n index end]-1}] [match_linux_wm [list frame $id.n$gfxstub]] -text $title -padding 6 + $id.n configure -style TNotebook + $id.n select 0 + wm title $id {Array Properties} + set id $id.n$gfxstub + } pdtk_panelkeybindings $id "array" global pd_nt ctrl_key pdtk_standardkeybindings $id #override panelkeybindings with an unusual ok/apply format - bind $id <KeyPress-Return> [format "array_ok $id $canvas"] + + if {$newone} { + bind $id <KeyPress-Return> [format "array_ok $id $canvas"] + } else { + bind $id <KeyPress-Return> [format "canvas_ok $mytoplevel"] + } match_linux_wm [list frame $id.name] pack $id.name -side top -pady 3 @@ -6312,70 +6450,116 @@ proc pdtk_array_dialog {id name n flags newone canvas} { pack $id.n -side top match_linux_wm [list label $id.n.label -text " size"] match_linux_wm [list entry $id.n.entry -textvariable $var_array_n] - pack $id.n.label $id.n.entry -side left -padx 3 + pack $id.n.label $id.n.entry -side left -padx 3 -pady 6 + + # hack so I don't have to rename everything + set old_id $id + set id [match_linux_wm [list frame $id.settings]] + pack $id match_linux_wm [list checkbutton $id.saveme -text {save contents} \ - -variable $var_array_saveit] - pack $id.saveme -side top -pady 3 + -variable $var_array_saveit] + pack $id.saveme -side top -pady 1 -anchor w + match_linux_wm [list checkbutton $id.joc -text {jump on click} \ + -variable $var_array_joc] + pack $id.joc -side top -pady 1 -anchor w + + set ffr $id.fillframe + set ofr $id.outlineframe + set olabel $id.outlineframe.l match_linux_wm [list frame $id.drawasrects] - pack $id.drawasrects -side top -pady 3 + pack $id.drawasrects -side top -pady 3 -anchor w + match_linux_wm [list label $id.drawasrects.l -text "draw as:"] + pack $id.drawasrects.l -side top -pady 3 -anchor w match_linux_wm [list radiobutton $id.drawasrects.drawasrects0 -value 0 \ -variable $var_array_drawasrects \ - -text "draw as points"] + -text "points" \ + -command "array_update_drawas 0 $ffr $ofr $olabel"] match_linux_wm [list radiobutton $id.drawasrects.drawasrects1 -value 1 \ -variable $var_array_drawasrects \ - -text "polygon"] + -text "polygon" \ + -command "array_update_drawas 1 $ffr $ofr $olabel"] #match_linux_wm [list radiobutton $id.drawasrects.drawasrects2 -value 2 \ # -variable $var_array_drawasrects \ - # -text "bezier curve"] - pack $id.drawasrects.drawasrects0 -side top - pack $id.drawasrects.drawasrects1 -side top - #pack $id.drawasrects.drawasrects2 -side top + # -text "bezier curve" \ + # -command "array_update_drawas 2 $ffr $ofr $olabel"] + match_linux_wm [list radiobutton $id.drawasrects.drawasrects3 -value 3 \ + -variable $var_array_drawasrects \ + -text "bar graph" \ + -command "array_update_drawas 3 $ffr $ofr $olabel"] + pack $id.drawasrects.drawasrects0 -side top -anchor w + pack $id.drawasrects.drawasrects1 -side top -anchor w + #pack $id.drawasrects.drawasrects2 -side top -anchor w + pack $id.drawasrects.drawasrects3 -side top -anchor w + + foreach attr {outline fill} { + set f [match_linux_wm [list frame $id.${attr}frame]] + pack $f -pady 5 -anchor w + button $f.b -relief raised -padx 7 -pady 0 \ + -background [set $attr] -activebackground [set $attr] \ + -command \ + "array_choosecolor $f.b $mytoplevel [set var_array_$attr]" + pack $f.b -side left -anchor w + match_linux_wm [list label $f.l -text "$attr color"] + pack $f.l -side left -anchor w + bind $f.l <Enter> "$f.l configure -foreground blue" + bind $f.l <Leave> "$f.l configure -foreground black" + bind $f.l <1> "$f.b invoke" + } + array_update_drawas [set $var_array_drawasrects] $ffr $ofr $olabel if {$newone != 0} { match_linux_wm [list frame $id.radio] - pack $id.radio -side top -pady 3 + pack $id.radio -side top -pady 3 -anchor w match_linux_wm [list radiobutton $id.radio.radio0 -value 0 \ -variable $var_array_otherflag \ -text "in new graph"] match_linux_wm [list radiobutton $id.radio.radio1 -value 1 \ -variable $var_array_otherflag \ -text "in last graph"] - pack $id.radio.radio0 -side top - pack $id.radio.radio1 -side top - } else { - match_linux_wm [list checkbutton $id.deleteme -text {delete me} \ - -variable $var_array_otherflag] - pack $id.deleteme -side top + pack $id.radio.radio0 -side top -anchor w + pack $id.radio.radio1 -side top -anchor w } + + set id $old_id + # jsarlo if {$newone == 0} { match_linux_wm [list button $id.listview -text {View list}\ - -command "array_viewlist $id"] - pack $id.listview -side left -padx 3 -pady 3 - } - # end jsarlo + -command "array_viewlist $gfxstub $mytoplevel"] + pack $id.listview -side right -padx 3 -pady 3 + match_linux_wm [list checkbutton $id.deleteme -text {delete me} \ + -variable $var_array_otherflag] + if {$multiarray_graph} { + pack $id.deleteme -side left + } + # end jsarlo + } else { match_linux_wm [list frame $id.buttonframe] pack $id.buttonframe -side bottom -fill x match_linux_wm [list button $id.buttonframe.cancel -text {Cancel}\ -command "array_cancel $id"] - if {$newone == 0} { - match_linux_wm [list button \ - $id.buttonframe.apply -text {Apply} \ - -command "array_apply $id $canvas"] - } +# if {$newone == 0} { +# match_linux_wm [list button \ +# $id.buttonframe.apply -text {Apply} \ +# -command "array_apply $id $canvas"] +# } match_linux_wm [list button $id.buttonframe.ok -text {OK} \ -command "array_ok $id $canvas"] pack $id.buttonframe.cancel -side left -expand 1 -pady 3 -padx 3 - if {$newone == 0} {pack $id.buttonframe.apply -side left -expand 1 -pady 3 -padx 3} - pack $id.buttonframe.ok -side left -expand 1 -pady 3 -padx 3 + if {$newone == 0} { + pack $id.buttonframe.apply -side left -expand 1 -pady 3 -padx 3 + } + if {$newone} {pack $id.buttonframe.ok -side left -expand 1 -pady 3 -padx 3} +} if { [info tclversion] < 8.5 } { $id.name.entry select from 0 $id.name.entry select adjust end } focus $id.name.entry +} fid]} {pdtk_post "array dialog error: $fid\n"} } ############ pdtk_canvas_dialog -- dialog window for canvass ######### @@ -6385,7 +6569,17 @@ proc canvas_apply {id} { # strip "." from the TK id to make a variable name suffix set vid [string trimleft $id .] # for each variable, make a local variable to hold its name... + foreach tab [$id.n tabs] { + set arraytab "" + if {[regexp [list $id\.n(\.gfxstub.+)] $tab - arrayid]} { + set arrayvid [string trimleft $arrayid .] + set var_array_canvas [concat array_canvas_$arrayvid] + global $var_array_canvas + array_apply $arrayid [set $var_array_canvas] + } + +} set var_canvas_xscale [concat canvas_xscale_$vid] global $var_canvas_xscale set var_canvas_yscale [concat canvas_yscale_$vid] @@ -6465,16 +6659,19 @@ proc canvas_checkcommand {id} { set var_canvas_ymargin [concat canvas_ymargin_$vid] global $var_canvas_ymargin + + set id $id.n.canvasdialog + if { [eval concat $$var_canvas_graphme] != 0 } { $id.hidetext configure -state normal - $id.xrange.entry1 configure -state normal - $id.xrange.entry2 configure -state normal - $id.xrange.entry3 configure -state normal - $id.xrange.entry4 configure -state normal - $id.yrange.entry1 configure -state normal - $id.yrange.entry2 configure -state normal - $id.yrange.entry3 configure -state normal - $id.yrange.entry4 configure -state normal + $id.x.f1.entry1 configure -state normal + $id.x.f1.entry2 configure -state normal + $id.x.f2.entry3 configure -state normal + $id.x.f2.entry4 configure -state normal + $id.y.f1.entry1 configure -state normal + $id.y.f1.entry2 configure -state normal + $id.y.f2.entry3 configure -state normal + $id.y.f2.entry4 configure -state normal $id.xscale.entry configure -state disabled $id.yscale.entry configure -state disabled set x1 [eval concat $$var_canvas_x1] @@ -6498,14 +6695,14 @@ proc canvas_checkcommand {id} { } } else { $id.hidetext configure -state disabled - $id.xrange.entry1 configure -state disabled - $id.xrange.entry2 configure -state disabled - $id.xrange.entry3 configure -state disabled - $id.xrange.entry4 configure -state disabled - $id.yrange.entry1 configure -state disabled - $id.yrange.entry2 configure -state disabled - $id.yrange.entry3 configure -state disabled - $id.yrange.entry4 configure -state disabled + $id.x.f1.entry1 configure -state disabled + $id.x.f1.entry2 configure -state disabled + $id.x.f2.entry3 configure -state disabled + $id.x.f2.entry4 configure -state disabled + $id.y.f1.entry1 configure -state disabled + $id.y.f1.entry2 configure -state disabled + $id.y.f2.entry3 configure -state disabled + $id.y.f2.entry4 configure -state disabled $id.xscale.entry configure -state normal $id.yscale.entry configure -state normal if { [eval concat $$var_canvas_xscale] == 0 } { @@ -6545,9 +6742,7 @@ proc pdtk_canvas_dialog_undo_update {name x y} { proc pdtk_canvas_dialog {id xscale yscale graphme x1 y1 x2 y2 \ xpix ypix xmargin ymargin} { set vid [string trimleft $id .] - #puts stderr $id - set var_canvas_xscale [concat canvas_xscale_$vid] global $var_canvas_xscale set var_canvas_yscale [concat canvas_yscale_$vid] @@ -6594,8 +6789,26 @@ proc pdtk_canvas_dialog {id xscale yscale graphme x1 y1 x2 y2 \ wm geometry $id "+$tmp_xpix+$tmp_ypix" wm protocol $id WM_DELETE_WINDOW [concat canvas_cancel $id] + ttk::style layout Plain.TNotebook.Tab {Notebook.tab -side left} + ttk::notebook $id.n -style Plain.TNotebook + $id.n add [match_linux_wm [list frame $id.n.canvasdialog]] \ + -text "Graph" -sticky nsew -padding 6 + + pack $id.n -fill x + # store the current canvas_dialog gfxstub id + # in a global variable. This will be fetched by + # pdtk_array_dialog so that it can append + # itself to the canvas dialog, rather than spawning + # multiple dialogs on top of each other. We can + # do this because canvas_properties creates a + # canvas dialog _before_ calling garray_properties-- + # that will guarantee that the global id set here + # is "fresh". + set ::pd_canvasdialog_current $id pdtk_panelkeybindings $id "canvas" + set wid $id + set id $id.n.canvasdialog #superfluous repetition of window title information #match_linux_wm [list label $id.toplabel -text "Canvas Properties"] @@ -6617,73 +6830,87 @@ proc pdtk_canvas_dialog {id xscale yscale graphme x1 y1 x2 y2 \ match_linux_wm [list checkbutton $id.graphme -text {graph on parent} \ -variable $var_canvas_graphme \ - -command [concat canvas_checkcommand $id]] + -command [concat canvas_checkcommand $wid]] pack $id.graphme -side top match_linux_wm [list checkbutton $id.hidetext \ -text {hide object name and arguments} \ -variable $var_canvas_hidetext \ - -command [concat canvas_checkcommand $id]] + -command [concat canvas_checkcommand $wid]] pack $id.hidetext -side top - match_linux_wm [list frame $id.xrange] - pack $id.xrange -side top - match_linux_wm [list label $id.xrange.label1 -text "X range: from"] - match_linux_wm [list entry $id.xrange.entry1 \ + match_linux_wm [list labelframe $id.x -text "X-axis"] + match_linux_wm [list frame $id.x.f1] + match_linux_wm [list frame $id.x.f2] + pack $id.x -side top -pady 6 + pack $id.x.f1 -side top -fill x + pack $id.x.f2 -side top -fill x + match_linux_wm [list label $id.x.f1.label1 -text "from"] + match_linux_wm [list entry $id.x.f1.entry1 \ -textvariable $var_canvas_x1 -width 6] - match_linux_wm [list label $id.xrange.label2 -text "to"] - match_linux_wm [list entry $id.xrange.entry2 \ + match_linux_wm [list label $id.x.f1.label2 -text "to"] + match_linux_wm [list entry $id.x.f1.entry2 \ -textvariable $var_canvas_x2 -width 6] - match_linux_wm [list label $id.xrange.label3 -text "size"] - match_linux_wm [list entry $id.xrange.entry3 \ + match_linux_wm [list label $id.x.f2.label3 -text "size"] + match_linux_wm [list entry $id.x.f2.entry3 \ -textvariable $var_canvas_xpix -width 4] - match_linux_wm [list label $id.xrange.label4 -text "margin"] - match_linux_wm [list entry $id.xrange.entry4 \ + match_linux_wm [list label $id.x.f2.label4 -text "margin"] + match_linux_wm [list entry $id.x.f2.entry4 \ -textvariable $var_canvas_xmargin -width 4] - pack $id.xrange.label1 $id.xrange.entry1 \ - $id.xrange.label2 $id.xrange.entry2 \ - $id.xrange.label3 $id.xrange.entry3 \ - $id.xrange.label4 $id.xrange.entry4 \ - -side left -pady 3 -padx 3 - - match_linux_wm [list frame $id.yrange] - pack $id.yrange -side top - match_linux_wm [list label $id.yrange.label1 -text "Y range: from"] - match_linux_wm [list entry $id.yrange.entry1 \ + pack $id.x.f1.label1 $id.x.f1.entry1 \ + $id.x.f1.label2 $id.x.f1.entry2 \ + -side left -pady 3 -padx 3 -expand 1 + pack $id.x.f2.label3 $id.x.f2.entry3 \ + $id.x.f2.label4 $id.x.f2.entry4 \ + -side left -pady 3 -padx 3 -expand 1 + + match_linux_wm [list labelframe $id.y -text "Y-axis"] + + match_linux_wm [list frame $id.y.f1] + match_linux_wm [list frame $id.y.f2] + pack $id.y -side top -pady 6 + pack $id.y.f1 -side top -fill x + pack $id.y.f2 -side top -fill x + + + pack $id.y -side top + match_linux_wm [list label $id.y.f1.label1 -text "from"] + match_linux_wm [list entry $id.y.f1.entry1 \ -textvariable $var_canvas_y1 -width 6] - match_linux_wm [list label $id.yrange.label2 -text "to"] - match_linux_wm [list entry $id.yrange.entry2 \ + match_linux_wm [list label $id.y.f1.label2 -text "to"] + match_linux_wm [list entry $id.y.f1.entry2 \ -textvariable $var_canvas_y2 -width 6] - match_linux_wm [list label $id.yrange.label3 -text "size"] - match_linux_wm [list entry $id.yrange.entry3 \ + match_linux_wm [list label $id.y.f2.label3 -text "size"] + match_linux_wm [list entry $id.y.f2.entry3 \ -textvariable $var_canvas_ypix -width 4] - match_linux_wm [list label $id.yrange.label4 -text "margin"] - match_linux_wm [list entry $id.yrange.entry4 \ + match_linux_wm [list label $id.y.f2.label4 -text "margin"] + match_linux_wm [list entry $id.y.f2.entry4 \ -textvariable $var_canvas_ymargin -width 4] - pack $id.yrange.label1 $id.yrange.entry1 \ - $id.yrange.label2 $id.yrange.entry2 \ - $id.yrange.label3 $id.yrange.entry3 \ - $id.yrange.label4 $id.yrange.entry4 \ - -side left -pady 3 -padx 3 - - match_linux_wm [list frame $id.buttonframe] - pack $id.buttonframe -side bottom -fill x - match_linux_wm [list button $id.buttonframe.cancel -text {Cancel}\ - -command "canvas_cancel $id"] - match_linux_wm [list button $id.buttonframe.apply -text {Apply}\ - -command "canvas_apply $id"] - match_linux_wm [list button $id.buttonframe.ok -text {OK}\ - -command "canvas_ok $id"] - pack $id.buttonframe.cancel -side left -expand 1 -pady 3 -padx 3 - pack $id.buttonframe.apply -side left -expand 1 -pady 3 -padx 3 - pack $id.buttonframe.ok -side left -expand 1 -pady 3 -padx 3 + pack $id.y.f1.label1 $id.y.f1.entry1 \ + $id.y.f1.label2 $id.y.f1.entry2 \ + -side left -pady 3 -padx 3 -expand 1 + pack $id.y.f2.label3 $id.y.f2.entry3 \ + $id.y.f2.label4 $id.y.f2.entry4 \ + -side left -pady 3 -padx 3 -expand 1 + + match_linux_wm [list frame $wid.buttonframe] + pack $wid.buttonframe -side bottom -fill x + match_linux_wm [list button $wid.buttonframe.cancel -text {Cancel}\ + -command "canvas_cancel $wid"] + match_linux_wm [list button $wid.buttonframe.apply -text {Apply}\ + -command "canvas_apply $wid"] + match_linux_wm [list button $wid.buttonframe.ok -text {OK}\ + -command "canvas_ok $wid"] + pack $wid.buttonframe.cancel -side left -expand 1 -pady 3 -padx 3 + pack $wid.buttonframe.apply -side left -expand 1 -pady 3 -padx 3 + pack $wid.buttonframe.ok -side left -expand 1 -pady 3 -padx 3 if { [info tclversion] < 8.5 } { $id.xscale.entry select from 0 $id.xscale.entry select adjust end } focus $id.xscale.entry - canvas_checkcommand $id + canvas_checkcommand $wid } ############ pdtk_data_dialog -- run a data dialog #########