[PD-cvs] pd/src desire.c,1.1.2.110,1.1.2.111

Mathieu Bouchard matju at users.sourceforge.net
Sun Aug 20 22:05:58 CEST 2006


Update of /cvsroot/pure-data/pd/src
In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv20073

Modified Files:
      Tag: devel_0_39
	desire.c 
Log Message:
fixing previous commits and preparing to merge g_rtext.c in


Index: desire.c
===================================================================
RCS file: /cvsroot/pure-data/pd/src/Attic/desire.c,v
retrieving revision 1.1.2.110
retrieving revision 1.1.2.111
diff -C2 -d -r1.1.2.110 -r1.1.2.111
*** desire.c	20 Aug 2006 19:56:01 -0000	1.1.2.110
--- desire.c	20 Aug 2006 20:05:55 -0000	1.1.2.111
***************
*** 4935,4939 ****
  void glist_add(t_glist *x, t_gobj *y)
  {
! /*
      if (!y->g_pd->c_patchable) {
  	printf("glist_add %p %p class=%s (non-t_text)\n",x,y,y->g_pd->c_name->s_name);
--- 4935,4939 ----
  void glist_add(t_glist *x, t_gobj *y)
  {
! 
      if (!y->g_pd->c_patchable) {
  	printf("glist_add %p %p class=%s (non-t_text)\n",x,y,y->g_pd->c_name->s_name);
***************
*** 4949,4953 ****
  	}
      }
! */
      gobj_subscribe(y,(t_gobj *)x);
  
--- 4949,4953 ----
  	}
      }
! 
      gobj_subscribe(y,(t_gobj *)x);
  
***************
*** 4957,4961 ****
      /* pd_upload(y); */
      /* if (glist_isvisible(x)) gobj_vis(y,x,1); */
!     if (glist_isvisible(x)) pd_upload(y);
  
      y->g_next = 0;
--- 4957,4962 ----
      /* pd_upload(y); */
      /* if (glist_isvisible(x)) gobj_vis(y,x,1); */
!     /* if (glist_isvisible(x)) pd_upload(y);*/
!     pd_upload(y);
  
      y->g_next = 0;
***************
*** 5010,5014 ****
      if (glist_isvisible(canvas)) {
  	/*!@#$ race condition because the queue might still contain something */
! 	sys_mgui(y,"_delete","");
      }
  
--- 5011,5015 ----
      if (glist_isvisible(canvas)) {
  	/*!@#$ race condition because the queue might still contain something */
! 	/*sys_mgui(y,"_delete","");*/ //???
      }
  
***************
*** 12910,12911 ****
--- 12911,13456 ----
      }
  }
+ 
+ /* ---------------------------------------------------------------- */
+ /* formerly g_rtext.c */
+ #if 0
+ #include <stdlib.h>
+ #include <string.h>
+ #include <stdio.h>
+ #include <ctype.h>
+ #include "m_pd.h"
+ #include "s_stuff.h"
+ #include "g_canvas.h"
+ #include "t_tk.h"
+ 
+ #define LMARGIN 1
+ #define RMARGIN 1
+ #define TMARGIN 2
+ #define BMARGIN 2
+ 
+ #define SEND_FIRST 1
+ #define SEND_UPDATE 2
+ #define SEND_CHECK 0
+ 
+ struct _rtext
+ {
+     char *x_buf;
+     int x_bufsize;
+     int x_selstart;
+     int x_selend;
+     int x_active;
+     int x_dragfrom;
+     int x_height;
+     int x_drawnwidth;
+     int x_drawnheight;
+     t_text *x_text;
+     t_glist *x_glist;
+     char x_tag[50];
+     struct _rtext *x_next;
+ };
+ 
+ t_rtext *rtext_new(t_glist *glist, t_text *who)
+ {
+     t_rtext *x = (t_rtext *)getbytes(sizeof *x);
+     int w = 0, h = 0, indx;
+     x->x_height = -1;
+     x->x_text = who;
+     x->x_glist = glist;
+     x->x_next = glist->gl_editor->e_rtext;
+     x->x_selstart = x->x_selend = x->x_active =
+         x->x_drawnwidth = x->x_drawnheight = 0;
+     binbuf_gettext(who->te_binbuf, &x->x_buf, &x->x_bufsize);
+     glist->gl_editor->e_rtext = x;
+     sprintf(x->x_tag, ".x%lx.t%lx", (t_int)glist_getcanvas(x->x_glist),
+         (t_int)x);
+     return (x);
+ }
+ 
+ static t_rtext *rtext_entered;
+ 
+ void rtext_free(t_rtext *x)
+ {
+     if (x->x_glist->gl_editor->e_textedfor == x)
+         x->x_glist->gl_editor->e_textedfor = 0;
+     if (x->x_glist->gl_editor->e_rtext == x)
+         x->x_glist->gl_editor->e_rtext = x->x_next;
+     else
+     {
+         t_rtext *e2;
+         for (e2 = x->x_glist->gl_editor->e_rtext; e2; e2 = e2->x_next)
+             if (e2->x_next == x)
+         {
+             e2->x_next = x->x_next;
+             break;
+         }
+     }
+     if (rtext_entered == x) rtext_entered = 0;
+     freebytes(x->x_buf, x->x_bufsize);
+     freebytes(x, sizeof *x);
+ }
+ 
+ char *rtext_gettag(t_rtext *x)
+ {
+     return (x->x_tag);
+ }
+ 
+ void rtext_gettext(t_rtext *x, char **buf, int *bufsize)
+ {
+     *buf = x->x_buf;
+     *bufsize = x->x_bufsize;
+ }
+ 
+ void rtext_getseltext(t_rtext *x, char **buf, int *bufsize)
+ {
+     *buf = x->x_buf + x->x_selstart;
+     *bufsize = x->x_selend - x->x_selstart;
+ }
+ 
+ /* LATER deal with tcl-significant characters */
+ 
+ static int firstone(char *s, int c, int n)
+ {
+     char *s2 = s + n;
+     int i = 0;
+     while (s != s2)
+     {
+         if (*s == c) return (i);
+         i++;
+         s++;
+     }
+     return (-1);
+ }
+ 
+ static int lastone(char *s, int c, int n)
+ {
+     char *s2 = s + n;
+     while (s2 != s)
+     {
+         s2--;
+         n--;
+         if (*s2 == c) return (n);
+     }
+     return (-1);
+ }
+ 
+     /* the following routine computes line breaks and carries out
+     some action which could be:
+         SEND_FIRST - draw the box  for the first time
+         SEND_UPDATE - redraw the updated box
+         otherwise - don't draw, just calculate.
+     Called with *widthp and *heightpas coordinates of
+     a test point, the routine reports the index of the character found
+     there in *indexp.  *widthp and *heightp are set to the width and height
+     of the entire text in pixels.
+     */
+ 
+     /* LATER get this and sys_vgui to work together properly,
+         breaking up messages as needed.  As of now, there's
+         a limit of 1950 characters, imposed by sys_vgui(). */
+ #define UPBUFSIZE 4000
+ #define BOXWIDTH 60
+ 
+ /* Older (pre-8.3.4) TCL versions handle text selection differently; this
+ flag is set from the GUI if this happens.  LATER take this out: early 2006? */
+ 
+ extern int sys_oldtclversion;           
+ 
+ static void rtext_senditup(t_rtext *x, int action, int *widthp, int *heightp,
+     int *indexp)
+ {
+     float dispx, dispy;
+     char smallbuf[200], *tempbuf;
+     int outchars = 0, nlines = 0, ncolumns = 0,
+         pixwide, pixhigh, font, fontwidth, fontheight, findx, findy;
+     int reportedindex = 0;
+     t_canvas *canvas = glist_getcanvas(x->x_glist);
+     int widthspec = x->x_text->te_width;
+     int widthlimit = (widthspec ? widthspec : BOXWIDTH);
+     int inindex = 0;
+     int selstart = 0, selend = 0;
+         /* if we're a GOP (the new, "goprect" style) borrow the font size
+         from the inside to preserve the spacing */
+     if (pd_class(&x->x_text->te_pd) == canvas_class &&
+         ((t_glist *)(x->x_text))->gl_isgraph &&
+         ((t_glist *)(x->x_text))->gl_goprect)
+             font =  glist_getfont((t_glist *)(x->x_text));
+     else font = glist_getfont(x->x_glist);
+     fontwidth = sys_fontwidth(font);
+     fontheight = sys_fontheight(font);
+     findx = (*widthp + (fontwidth/2)) / fontwidth;
+     findy = *heightp / fontheight;
+     if (x->x_bufsize >= 100)
+          tempbuf = (char *)t_getbytes(2 * x->x_bufsize + 1);
+     else tempbuf = smallbuf;
+     while (x->x_bufsize - inindex > 0)
+     {
+         int inchars = x->x_bufsize - inindex;
+         int maxindex = (inchars > widthlimit ? widthlimit : inchars);
+         int eatchar = 1;
+         int foundit = firstone(x->x_buf + inindex, '\n', maxindex);
+         if (foundit < 0)
+         {
+             if (inchars > widthlimit)
+             {
+                 foundit = lastone(x->x_buf + inindex, ' ', maxindex);
+                 if (foundit < 0)
+                 {
+                     foundit = maxindex;
+                     eatchar = 0;
+                 }
+             }
+             else
+             {
+                 foundit = inchars;
+                 eatchar = 0;
+             }
+         }
+         if (nlines == findy)
+         {
+             int actualx = (findx < 0 ? 0 :
+                 (findx > foundit ? foundit : findx));
+             *indexp = inindex + actualx;
+             reportedindex = 1;
+         }
+         strncpy(tempbuf+outchars, x->x_buf + inindex, foundit);
+         if (x->x_selstart >= inindex &&
+             x->x_selstart <= inindex + foundit + eatchar)
+                 selstart = x->x_selstart + outchars - inindex;
+         if (x->x_selend >= inindex &&
+             x->x_selend <= inindex + foundit + eatchar)
+                 selend = x->x_selend + outchars - inindex;
+         outchars += foundit;
+         inindex += (foundit + eatchar);
+         if (inindex < x->x_bufsize)
+             tempbuf[outchars++] = '\n';
+         if (foundit > ncolumns)
+             ncolumns = foundit;
+         nlines++;
+     }
+     if (!reportedindex)
+         *indexp = outchars;
+     dispx = text_xpix(x->x_text, x->x_glist);
+     dispy = text_ypix(x->x_text, x->x_glist);
+     if (nlines < 1) nlines = 1;
+     if (!widthspec)
+     {
+         while (ncolumns < 3)
+         {
+             tempbuf[outchars++] = ' ';
+             ncolumns++;
+         }
+     }
+     else ncolumns = widthspec;
+     pixwide = ncolumns * fontwidth + (LMARGIN + RMARGIN);
+     pixhigh = nlines * fontheight + (TMARGIN + BMARGIN);
+ 
+     if (action == SEND_FIRST)
+         sys_vgui("pdtk_text_new .x%lx.c %s %f %f {%.*s} %d %s\n",
+             canvas, x->x_tag,
+             dispx + LMARGIN, dispy + TMARGIN,
+             outchars, tempbuf, sys_hostfontsize(font),
+             (glist_isselected(x->x_glist,
+                 &x->x_glist->gl_gobj)? "blue" : "black"));
+     else if (action == SEND_UPDATE)
+     {
+         sys_vgui("pdtk_text_set .x%lx.c %s {%.*s}\n",
+             canvas, x->x_tag, outchars, tempbuf);
+         if (pixwide != x->x_drawnwidth || pixhigh != x->x_drawnheight) 
+             text_drawborder(x->x_text, x->x_glist, x->x_tag,
+                 pixwide, pixhigh, 0);
+         if (x->x_active)
+         {
+             if (selend > selstart)
+             {
+                 sys_vgui(".x%lx.c select from %s %d\n", canvas, 
+                     x->x_tag, selstart);
+                 sys_vgui(".x%lx.c select to %s %d\n", canvas, 
+                     x->x_tag, selend + (sys_oldtclversion ? 0 : -1));
+                 sys_vgui(".x%lx.c focus \"\"\n", canvas);        
+             }
+             else
+             {
+                 sys_vgui(".x%lx.c select clear\n", canvas);
+                 sys_vgui(".x%lx.c icursor %s %d\n", canvas, x->x_tag,
+                     selstart);
+                 sys_vgui(".x%lx.c focus %s\n", canvas, x->x_tag);        
+             }
+         }
+     }
+     x->x_drawnwidth = pixwide;
+     x->x_drawnheight = pixhigh;
+     
+     *widthp = pixwide;
+     *heightp = pixhigh;
+     if (tempbuf != smallbuf)
+         t_freebytes(tempbuf, 2 * x->x_bufsize + 1);
+ }
+ 
+ void rtext_retext(t_rtext *x)
+ {
+     int w = 0, h = 0, indx;
+     t_text *text = x->x_text;
+     t_freebytes(x->x_buf, x->x_bufsize);
+     binbuf_gettext(text->te_binbuf, &x->x_buf, &x->x_bufsize);
+         /* special case: for number boxes, try to pare the number down
+         to the specified width of the box. */
+     if (text->te_width > 0 && text->te_type == T_ATOM &&
+         x->x_bufsize > text->te_width)
+     {
+         t_atom *atomp = binbuf_getvec(text->te_binbuf);
+         int natom = binbuf_getnatom(text->te_binbuf);
+         int bufsize = x->x_bufsize;
+         if (natom == 1 && atomp->a_type == A_FLOAT)
+         {
+                 /* try to reduce size by dropping decimal digits */
+             int wantreduce = bufsize - text->te_width;
+             char *decimal = 0, *nextchar, *ebuf = x->x_buf + bufsize,
+                 *s1, *s2;
+             int ndecimals;
+             for (decimal = x->x_buf; decimal < ebuf; decimal++)
+                 if (*decimal == '.')
+                     break;
+             if (decimal >= ebuf)
+                 goto giveup;
+             for (nextchar = decimal + 1; nextchar < ebuf; nextchar++)
+                 if (*nextchar < '0' || *nextchar > '9')
+                     break;
+             if (nextchar - decimal - 1 < wantreduce)
+                 goto giveup;
+             for (s1 = nextchar - wantreduce, s2 = s1 + wantreduce;
+                 s2 < ebuf; s1++, s2++)
+                     *s1 = *s2;
+             x->x_buf = t_resizebytes(x->x_buf, bufsize, text->te_width);
+             bufsize = text->te_width;
+             goto done;
+         giveup:
+                 /* give up and bash it to "+" or "-" */
+             x->x_buf[0] = (atomp->a_w.w_float < 0 ? '-' : '+');
+             x->x_buf = t_resizebytes(x->x_buf, bufsize, 1);
+             bufsize = 1;
+         }
+         else if (bufsize > text->te_width)
+         {
+             x->x_buf[text->te_width - 1] = '>';
+             x->x_buf = t_resizebytes(x->x_buf, bufsize, text->te_width);
+             bufsize = text->te_width;
+         }
+     done:
+         x->x_bufsize = bufsize;
+     }
+     rtext_senditup(x, SEND_UPDATE, &w, &h, &indx);
+ }
+ 
+ /* find the rtext that goes with a text item */
+ t_rtext *glist_findrtext(t_glist *gl, t_text *who)
+ {
+     t_rtext *x = gl->gl_editor->e_rtext;
+     while (x && x->x_text != who) x = x->x_next;
+     if (!x) bug("glist_findrtext");
+     return (x);
+ }
+ 
+ int rtext_width(t_rtext *x)
+ {
+     int w = 0, h = 0, indx;
+     rtext_senditup(x, SEND_CHECK, &w, &h, &indx);
+     return (w);
+ }
+ 
+ int rtext_height(t_rtext *x)
+ {
+     int w = 0, h = 0, indx;
+     rtext_senditup(x, SEND_CHECK, &w, &h, &indx);
+     return (h);
+ }
+ 
+ void rtext_draw(t_rtext *x)
+ {
+     int w = 0, h = 0, indx;
+     rtext_senditup(x, SEND_FIRST, &w, &h, &indx);
+ }
+ 
+ void rtext_erase(t_rtext *x)
+ {
+     sys_vgui(".x%lx.c delete %s\n", glist_getcanvas(x->x_glist), x->x_tag);
+ }
+ 
+ void rtext_displace(t_rtext *x, int dx, int dy)
+ {
+     sys_vgui(".x%lx.c move %s %d %d\n", glist_getcanvas(x->x_glist), 
+         x->x_tag, dx, dy);
+ }
+ 
+ void rtext_select(t_rtext *x, int state)
+ {
+     t_glist *glist = x->x_glist;
+     t_canvas *canvas = glist_getcanvas(glist);
+     sys_vgui(".x%lx.c itemconfigure %s -fill %s\n", canvas, 
+         x->x_tag, (state? "blue" : "black"));
+     canvas_editing = canvas;
+ }
+ 
+ void rtext_activate(t_rtext *x, int state)
+ {
+     int w = 0, h = 0, indx;
+     t_glist *glist = x->x_glist;
+     t_canvas *canvas = glist_getcanvas(glist);
+     if (state)
+     {
+         sys_vgui(".x%lx.c focus %s\n", canvas, x->x_tag);
+         glist->gl_editor->e_textedfor = x;
+         glist->gl_editor->e_textdirty = 0;
+         x->x_dragfrom = x->x_selstart = 0;
+         x->x_selend = x->x_bufsize;
+         x->x_active = 1;
+     }
+     else
+     {
+         sys_vgui("selection clear .x%lx.c\n", canvas);
+         sys_vgui(".x%lx.c focus \"\"\n", canvas);
+         if (glist->gl_editor->e_textedfor == x)
+             glist->gl_editor->e_textedfor = 0;
+         x->x_active = 0;
+     }
+     rtext_senditup(x, SEND_UPDATE, &w, &h, &indx);
+ }
+ 
+ void rtext_key(t_rtext *x, int keynum, t_symbol *keysym)
+ {
+     int w = 0, h = 0, indx, i, newsize, ndel;
+     char *s1, *s2;
+     if (keynum)
+     {
+         int n = keynum;
+         if (n == '\r') n = '\n';
+         if (n == '\b')  /* backspace */
+         {
+                     /* LATER delete the box if all text is selected...
+                     this causes reentrancy problems now. */
+             /* if ((!x->x_selstart) && (x->x_selend == x->x_bufsize))
+             {
+                 ....
+             } */
+             if (x->x_selstart && (x->x_selstart == x->x_selend))
+                 x->x_selstart--;
+         }
+         else if (n == 127)      /* delete */
+         {
+             if (x->x_selend < x->x_bufsize && (x->x_selstart == x->x_selend))
+                 x->x_selend++;
+         }
+         
+         ndel = x->x_selend - x->x_selstart;
+         for (i = x->x_selend; i < x->x_bufsize; i++)
+             x->x_buf[i- ndel] = x->x_buf[i];
+         newsize = x->x_bufsize - ndel;
+         x->x_buf = (char *)resizebytes(x->x_buf, x->x_bufsize, newsize);
+         x->x_bufsize = newsize;
+ 
+         if (n == '\n' || isprint(n))
+         {
+             newsize = x->x_bufsize+1;
+             x->x_buf = (char *)resizebytes(x->x_buf, x->x_bufsize, newsize);
+             for (i = x->x_bufsize; i > x->x_selstart; i--)
+                 x->x_buf[i] = x->x_buf[i-1];
+             x->x_buf[x->x_selstart] = n;
+             x->x_bufsize = newsize;
+             x->x_selstart = x->x_selstart + 1;
+         }
+         x->x_selend = x->x_selstart;
+         x->x_glist->gl_editor->e_textdirty = 1;
+     }
+     else if (!strcmp(keysym->s_name, "Right"))
+     {
+         if (x->x_selend == x->x_selstart && x->x_selstart < x->x_bufsize)
+             x->x_selend = x->x_selstart = x->x_selstart + 1;
+         else
+             x->x_selstart = x->x_selend;
+     }
+     else if (!strcmp(keysym->s_name, "Left"))
+     {
+         if (x->x_selend == x->x_selstart && x->x_selstart > 0)
+             x->x_selend = x->x_selstart = x->x_selstart - 1;
+         else
+             x->x_selend = x->x_selstart;
+     }
+         /* this should be improved...  life's too short */
+     else if (!strcmp(keysym->s_name, "Up"))
+     {
+         if (x->x_selstart)
+             x->x_selstart--;
+         while (x->x_selstart > 0 && x->x_buf[x->x_selstart] != '\n')
+             x->x_selstart--;
+         x->x_selend = x->x_selstart;
+     }
+     else if (!strcmp(keysym->s_name, "Down"))
+     {
+         while (x->x_selend < x->x_bufsize &&
+             x->x_buf[x->x_selend] != '\n')
+             x->x_selend++;
+         if (x->x_selend < x->x_bufsize)
+             x->x_selend++;
+         x->x_selstart = x->x_selend;
+     }
+     rtext_senditup(x, SEND_UPDATE, &w, &h, &indx);
+ }
+ 
+ void rtext_mouse(t_rtext *x, int xval, int yval, int flag)
+ {
+     int w = xval, h = yval, indx;
+     rtext_senditup(x, SEND_CHECK, &w, &h, &indx);
+     if (flag == RTEXT_DOWN)
+     {
+         x->x_dragfrom = x->x_selstart = x->x_selend = indx;
+     }
+     else if (flag == RTEXT_DBL)
+     {
+         int whereseparator, newseparator;
+         x->x_dragfrom = -1;
+         whereseparator = 0;
+         if ((newseparator = lastone(x->x_buf, ' ', indx)) > whereseparator)
+             whereseparator = newseparator+1;
+         if ((newseparator = lastone(x->x_buf, '\n', indx)) > whereseparator)
+             whereseparator = newseparator+1;
+         if ((newseparator = lastone(x->x_buf, ';', indx)) > whereseparator)
+             whereseparator = newseparator+1;
+         if ((newseparator = lastone(x->x_buf, ',', indx)) > whereseparator)
+             whereseparator = newseparator+1;
+         x->x_selstart = whereseparator;
+         
+         whereseparator = x->x_bufsize - indx;
+         if ((newseparator =
+             firstone(x->x_buf+indx, ' ', x->x_bufsize - indx)) >= 0 &&
+                 newseparator < whereseparator)
+                     whereseparator = newseparator;
+         if ((newseparator =
+             firstone(x->x_buf+indx, '\n', x->x_bufsize - indx)) >= 0 &&
+                 newseparator < whereseparator)
+                     whereseparator = newseparator;
+         if ((newseparator =
+             firstone(x->x_buf+indx, ';', x->x_bufsize - indx)) >= 0 &&
+                 newseparator < whereseparator)
+                     whereseparator = newseparator;
+         if ((newseparator =
+             firstone(x->x_buf+indx, ',', x->x_bufsize - indx)) >= 0 &&
+                 newseparator < whereseparator)
+                     whereseparator = newseparator;
+         x->x_selend = indx + whereseparator;
+     }
+     else if (flag == RTEXT_SHIFT)
+     {
+         if (indx * 2 > x->x_selstart + x->x_selend)
+             x->x_dragfrom = x->x_selstart, x->x_selend = indx;
+         else
+             x->x_dragfrom = x->x_selend, x->x_selstart = indx;
+     }
+     else if (flag == RTEXT_DRAG)
+     {
+         if (x->x_dragfrom < 0)
+             return;
+         x->x_selstart = (x->x_dragfrom < indx ? x->x_dragfrom : indx);
+         x->x_selend = (x->x_dragfrom > indx ? x->x_dragfrom : indx);
+     }
+     rtext_senditup(x, SEND_UPDATE, &w, &h, &indx);
+ }
+ #endif /*0*/
\ No newline at end of file





More information about the Pd-cvs mailing list