/* @(#)idiutil2.c	19.1 (ESO-DMD) 02/25/03 13:54:47 */
/*===========================================================================
  Copyright (C) 1995 European Southern Observatory (ESO)
 
  This program is free software; you can redistribute it and/or 
  modify it under the terms of the GNU General Public License as 
  published by the Free Software Foundation; either version 2 of 
  the License, or (at your option) any later version.
 
  This program is distributed in the hope that it will be useful,
  but WITHOUT ANY WARRANTY; without even the implied warranty of
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  GNU General Public License for more details.
 
  You should have received a copy of the GNU General Public 
  License along with this program; if not, write to the Free 
  Software Foundation, Inc., 675 Massachusetts Ave, Cambridge, 
  MA 02139, USA.
 
  Correspondence concerning ESO-MIDAS should be addressed as follows:
	Internet e-mail: midas@eso.org
	Postal address: European Southern Observatory
			Data Management Division 
			Karl-Schwarzschild-Strasse 2
			D 85748 Garching bei Muenchen 
			GERMANY
===========================================================================*/

/***********************************************************************
*                                                                      *
*   file: idiutil2.c                                                   *
*                                                                      *
*   X11 independent internal service routines                          *
*                                                                      *
************************************************************************
* V 1.1  871201: P. Santin  - Trieste Astronomical Observatory (X10)   *
* V 2.0  890102: K. Banse - ESO Garching   (from now on)               *
 
 010522		last modif
 
************************************************************************

* contains the following routines:
*
*   allrefr              : Display Refresh of memories , cursors and roi
*   rectrefr             : Display Refresh of rect_memories
*   clgraph              : Clear graphics of a memory
*   curmove              : Interactive Cursor Movement;
*   loc_mod              : Modify Locator Data;
*   loc_zero             : Zero Locator Data;
*   polyclear            : Clear a polyline;
*   roimodify            : Interactive Region of Interest Modify;
*   roimove              : Interactive Region of Interest Move;
*   txtclear             : Clear a text string;
*   copy_over            : Copy overlay graphics to image channel
*   
***********************************************************************/


# include    <idi.h> 
# include    <idistruct.h>
# include    <proto_idi.h>


static int  epsi2 = 2;		/* must be synchronized with send_event */
				/* in module idilocal3.c !  */
static int  movcount = 0;
static int  temp;
static int  xdif, ydif;
static int  x, y, dxsize, dysize;

static unsigned char  pixls[2];

static LOCATOR  *loca;


/*

*/

/* ---- Refresh ------------------------------------------------------ */

/* general refresh of image memories                                   */

void allrefr(dspno,mem,memid,flag)
int       dspno, memid, flag;
MEM_DATA  *mem;

{
int    i, sx, sy, dx, dy;
CONF_DATA  *conf;
ALPH_DATA  *alph;


conf = ididev[dspno].confptr;

if (memid != conf->overlay)
   {
   if (mem->mmbm == (char *) 0) 
      i = allo_mem(dspno,mem,memid);

   if (ididev[dspno].devtyp == 'g') 
      cl_win(dspno,-1);			/* ensure right background colour */

   sx = mem->xscroll;
   if (sx >= 0) 
      dx = 0;
   else
      {
      dx = -sx;
      sx = 0;
      }

   sy = mem->ysize - (ididev[dspno].ysize + mem->yscroll);
   if (sy >= 0)
      dy = 0;
   else
      {
      dy = -sy;
      sy = 0;
      }

   smv(flag,dspno,mem,memid,sx,sy,mem->xsize,mem->ysize,dx,dy);

   if (ididev[dspno].alpno >= 90)
      {
      alph = conf->alpmem[memid];
      alprfr(dspno,alph);
      }
   }

if (flag != 0)				/* we don't come from IIZWSC_C  */
   {
   if (mem->gpntr != 0) polyrefr(dspno,mem,0,0);
   if (mem->tpntr != 0) txtrefr(dspno,mem,0,0);
   }

}
/*

*/

/* refresh only rectangles of image memories                            */

void rectrefr(dspno,mem,memid)
int     dspno, memid;
MEM_DATA  *mem;

{
int    flag, sx, sy, dx, dy;

CONF_DATA  *conf;

ALPH_DATA  *alph;



conf = ididev[dspno].confptr;

if (mem->mmbm != (char *) 0)
   {
   sx = mem->xscroll + mem->xwoff;
   dx = mem->xwoff;

   sy = mem->ysize - (mem->ywoff + mem->ywdim);
   dy = ididev[dspno].ysize - (mem->ywoff+mem->ywdim);

   if (mem->zoom > 1)
      flag = 1;
   else
      flag = 11;			/* to update only a rectangle */
   smv(flag,dspno,mem,memid,sx,sy,mem->xwdim,mem->ywdim,dx,dy);

   if (ididev[dspno].alpno >= 90)
      {
      alph = conf->alpmem[memid];
      alprfr(dspno,alph);
      }
   }
}

/*

*/

/* ---- Clear Graphics ------------------------------------------- */

void clgraph(mem)

MEM_DATA  *mem;

{
GLIST     *gp;
TLIST     *tp;

if (mem->gpntr != 0)
   {
   gp = mem->gpntr;
   gp->geln = 0;
   *gp->off = 0;
   }

if (mem->tpntr != (TLIST *)0)
   {
   tp = mem->tpntr;
   tp->teln = 0;
   tp->off[0] = 0;
   }

}

/*

*/

/* ---- locator positions zero --------------------------------------- */

void loc_zero (dspno)
int dspno;

{
ROI_DATA   *roi;

register int loopi;


for (loopi=0; loopi<intdevtable[dspno].nloc; loopi++)
   {
   loca = intdevtable[dspno].loc[loopi];
   loca->xpos = 0;
   loca->ypos = 0;
   loca->xdif = 0;
   loca->ydif = 0;
   loca->lowsp = 1;
   loca->spfact = 0;			/* not used...  */
   loca->speed = loca->lowsp;
   }

roi = ididev[dspno].roi;
roi->radno = 4;			/* reset to default */
}

/*

*/

/* ---- locator modify ----------------------------------------------- */


void loc_mod(dspno,locno,lkey)

int   dspno, locno, lkey;

/* dspno    : display no.                */
/* locno    : locator no.                */
/* lkey     : locator key                */

{
static int locinc[10] = {0,1,2,4,8,16,32,64,100,200};

ROI_DATA   *roi;


if ((lkey < 10) && (lkey != -5))
   {
   if (lkey < -10)				/* just update */
      {
      roi = ididev[dspno].roi;
      roi->radno = -(lkey + 10);	/* -11,-12,-13,... => 1,2,3,... */
      if (roi->radno == 2)
         roi->ymax = roi->xmax - roi->radiusm;		/* distance value */
      else if (roi->radno == 3)
         roi->ymax = roi->xmax - roi->radiuso;
      else 
         roi->ymax = roi->xmax - roi->radiusi;
      }

   else
      {
      loca = intdevtable[dspno].loc[locno];

      if (lkey < 0)
         {
         if (lkey == -1)		/* update locator positions  */
            {
            loca->xdif = 0;
            loca->ydif = loca->speed;
            loca->ypos += loca->ydif;
            }
         else if (lkey == -2)
            {
            loca->xdif = 0;
            loca->ydif = - loca->speed;
            loca->ypos += loca->ydif;
            }
         else if (lkey == -3)
            {
            loca->ydif = 0;
            loca->xdif = loca->speed;
            loca->xpos += loca->xdif;
            }
         else 
            {
            loca->ydif = 0;
            loca->xdif = - loca->speed;
            loca->xpos += loca->xdif;
            }
         }
      else
         loca->speed = loca->lowsp + locinc[lkey];
      }
   }   
}

/*

*/

/* ---- cursor move -------------------------------------------------- */

/* curno    : cursor number                */
/* locno    : locator no.                  */
/* ldat     : locator data            */
/* lpos     : locator positions            */

void curmove (dspno,curno,locno,ldat,lpos)

int       dspno, curno, locno, ldat, *lpos;

{
CURS_DATA      *curs;

int   kk, jj;


curs = ididev[dspno].cursor[curno];
loca = intdevtable[dspno].loc[locno];
dxsize = ididev[dspno].xsize - 1;
dysize = ididev[dspno].ysize - 1;


/* depending on type of locator we compute new location or just read it  */

if (locno > 0)				/* if it's the arrow keys ... */
   {
   loc_mod(dspno,locno,ldat);
   xdif = loca->xdif;
   ydif = loca->ydif;
   loca->xdif = 0;
   loca->ydif = 0;
   if ((xdif == 0) && (ydif == 0)) return;	/* nothing to do */
   
   curs->xpos += xdif;
   curs->ypos += ydif;
   }

else
   {
   if ((lpos[0] == loca->xpos) && (lpos[1] == loca->ypos)) return;

   loca->xpos = lpos[0];
   loca->ypos = lpos[1];
   
   curs->xpos = loca->xpos + epsi2;
   curs->ypos = dysize - loca->ypos + epsi2;
   }

if (curs->xpos < 0)
   curs->xpos = 0;
else
   {
   if (curs->xpos > dxsize) curs->xpos = dxsize;
   }
if (curs->ypos < 0)
   curs->ypos = 0;
else
   {
   if (curs->ypos > dysize) curs->ypos = dysize;
   }

draw_curs(dspno,1,dysize,curno,curs->xpos,curs->ypos,curs->sh,curs->col);
show_pix8(dspno,curno,curs->xpos,curs->ypos,curs->xpos,curs->ypos,pixls);

if (++movcount == 3)
   {
   movcount = 0;
   jj = 0;
sh_loop:
   kk = ididev[dspno].shadow[jj++];
   if (kk != -1)
      { 
      draw_curs(kk,1,dysize,curno,curs->xpos,curs->ypos,curs->sh,curs->col);
      show_pix8(kk,curno,curs->xpos,curs->ypos,curs->xpos,curs->ypos,pixls);
      goto sh_loop;
      }
   }

}

/*

*/

/* ---- roi move ----------------------------------------------------- */

void roimove (dspno,locno,lpos)

int       dspno, locno, *lpos;

{
int    cposx, cposy;
int    xd1, xd2, yd1, yd2;
int    xmi,xma,ymi,yma;
int    kk, jj;
register int  ra, rb;

ROI_DATA       *roi;



loca = intdevtable[dspno].loc[locno];
if ((lpos[0] == loca->xpos) && (lpos[1] == loca->ypos)) return;

roi = ididev[dspno].roi;
dxsize = ididev[dspno].xsize  -1;
dysize = ididev[dspno].ysize  -1;

ra = lpos[0] + epsi2;				/* new center */
rb = dysize - lpos[1] + epsi2;

if (roi->sh == 0)			/* rectangle */
   {
   cposx = (roi->xmin + roi->xmax) / 2;		/* old center */
   cposy = (roi->ymin + roi->ymax) / 2;
   xd1 = cposx - roi->xmin;			/* distance to borders */
   xd2 = roi->xmax - cposx;
   yd1 = cposy - roi->ymin;
   yd2 = roi->ymax - cposy;


/* if we are at the window border, we stay put  */

   xmi = ra - xd1;
   if ((xmi < 0) || (xmi > dxsize)) return;
   xma = ra + xd2;
   if (xma < xmi) 
      xma = xmi;
   else
      {
      if (xma > dxsize) return;
      }
   ymi = rb - yd1;
   if ((ymi < 0) || (ymi > dysize)) return;
   yma = rb + yd2;
   if (yma < ymi)
      yma = ymi;
   else
      {
      if (yma > dysize) return;
      }


/*  update locator position  */

   
   roi->xmin = xmi;
   roi->xmax = xma;
   roi->ymin = ymi;
   roi->ymax = yma;
   draw_rroi(dspno,1,dysize,roi->xmin,roi->ymin,roi->xmax,roi->ymax,roi->col);
   show_pix8(dspno,2,roi->xmin,roi->ymin,roi->xmax,roi->ymax,pixls);
   }

else					/* circle(s) */
   {

/* if we are at the window border, we stay put  */

   xmi = ra - roi->radiusi;
   if ((xmi < 0) || (xmi > dxsize)) return;
   xma = ra + roi->radiusi;
   if ((xma < 0) || (xma > dxsize)) return;
   ymi = rb - roi->radiusi;
   if ((ymi < 0) || (ymi > dysize)) return;
   yma = rb + roi->radiusi;
   if ((yma < 0) || (yma > dysize)) return;
 
   roi->xmin = ra;
   roi->ymin = rb;
   draw_croi(dspno,1,dysize,roi->xmin,roi->ymin,
             roi->radiusi,roi->radiusm,roi->radiuso,roi->col);
   show_pix8(dspno,0,roi->xmin,roi->ymin,roi->xmin,roi->ymin,pixls);
   }

loca->xpos = lpos[0];
loca->ypos = lpos[1];


if (++movcount == 3)
   {
   movcount = 0;
   jj = 0;
sh_loop:
   kk = ididev[dspno].shadow[jj++];
   if (kk != -1)
      {
      if (roi->sh == 0)
         {
         draw_rroi(kk,1,dysize,roi->xmin,roi->ymin,roi->xmax,roi->ymax,
                   roi->col);
         show_pix8(kk,2,roi->xmin,roi->ymin,roi->xmax,roi->ymax,pixls);
         }
      else
         {
         draw_croi(kk,1,dysize,roi->xmin,roi->ymin,
                   roi->radiusi,roi->radiusm,roi->radiuso,roi->col);
         show_pix8(kk,0,roi->xmin,roi->ymin,roi->xmin,roi->ymin,pixls);
         }
      goto sh_loop;
      }
   }

}

/*

*/

/* ---- roi modify --------------------------------------------------- */

void roimodify (dspno,locno)

int      dspno, locno;

{
int   kk, jj;
register int  ra, rb;

ROI_DATA       *roi;


loca = intdevtable[dspno].loc[locno];

x = loca->xdif;    y = loca->ydif;
loca->xdif = 0;   loca->ydif = 0;

roi = ididev[dspno].roi;
dysize = ididev[dspno].ysize - 1;

if (roi->sh == 0)			/* rectangle */
   {
   ra = roi->xmax;
   rb = roi->ymax;

   if (x != 0)
      {
      ra += x;
      if (ra < 0)
         ra = 0;
      else
         {
         dxsize = ididev[dspno].xsize - 1;
         if (ra > dxsize) ra = dxsize;
         }
      if (ra < roi->xmin) ra = roi->xmin;
      }
   else
      {
      if (y == 0) return;		/* x=0 and y=0, => nothing to do */
      }

   if (y != 0)
      {
      rb += y;
      if (rb < 0)
         rb = 0;
      else
         {
         if (rb > dysize) rb = dysize;
         }
      if (rb < roi->ymin) rb = roi->ymin;
      }

   roi->xmax = ra;
   roi->ymax = rb;
   draw_rroi(dspno,1,dysize,roi->xmin,roi->ymin,roi->xmax,roi->ymax,roi->col);
   show_pix8(dspno,2,roi->xmin,roi->ymin,roi->xmax,roi->ymax,pixls);
   }

else					/* circle(s) */
   {
   if (x == 0)
      {
      if (y == 0) return;               /* x=0 and y=0, => nothing to do */
      x = y;				/* so we only use x */
      }
   rb = (roi->xmax + x) - roi->ymax;	/* new rad = new ref_rad - distance */
 

/*  update according to function keys F1, F2, F3 or F4 */

   if (roi->radno == 2)			/* only middle radius */
      {
      if (roi->radiusm < 1) return;
      if (rb == roi->radiusm)
         {
         if (x < 0)
            rb -- ;           /* for x/y = -1 */
         else
            rb ++ ;           /* for x/y = +1 */
         }

      if ((roi->radiuso > 0) && (rb > roi->radiuso)) rb = roi->radiuso;
      if (rb < roi->radiusi) rb = roi->radiusi;

      roi->radiusm = rb;
      }

   else if (roi->radno == 3)		/* only outer radius */
      {
      if (roi->radiuso < 1) return;
      if (rb == roi->radiuso)
         {
         if (x < 0)
            rb -- ;           /* for x/y = -1 */
         else
            rb ++ ;           /* for x/y = +1 */
         }

      if (roi->radiusm > 0)
         {
         if (rb < roi->radiusm) rb = roi->radiusm;
         }
      else
         {
         if (rb < roi->radiusi) rb = roi->radiusi;
         }

      roi->radiuso = rb;
      }

   else
      {
      if (rb == roi->radiusi)
         {
         if (x < 0) 
            rb -- ;		/* for x/y = -1 */
         else
            rb ++ ;		/* for x/y = +1 */
         }
      if (rb < 1) rb = 1;		/* at least 1 pixel radius */

      if (roi->radno == 4)	/* change inner circle + others (relative) */
         {
         ra = rb - roi->radiusi;	/* diff. of new + old radius  */
         if (roi->radiusm > 0) roi->radiusm += ra;
         if (roi->radiuso > 0) roi->radiuso += ra;
         }
      else 				/* only inner radius */
         {
         if (roi->radiusm > 0) 
            {
            if (rb > roi->radiusm) rb = roi->radiusm;
            }
         else if (roi->radiuso > 0) 
            {
            if (rb > roi->radiuso) rb = roi->radiuso;
            }
         }
      roi->radiusi = rb;
      }
   roi->xmax =  rb + roi->ymax;		/* update ref_radius */

   draw_croi(dspno,1,dysize,roi->xmin,roi->ymin,
             roi->radiusi,roi->radiusm,roi->radiuso,roi->col);
   show_pix8(dspno,0,roi->xmin,roi->ymin,roi->xmin,roi->ymin,pixls);
   }

jj = 0;
sh_loop:
kk = ididev[dspno].shadow[jj++];
if (kk != -1)
   {
   if (roi->sh == 0)
      {
      draw_rroi(kk,1,dysize,roi->xmin,roi->ymin,roi->xmax,roi->ymax,
                roi->col);
      show_pix8(kk,2,roi->xmin,roi->ymin,roi->xmax,roi->ymax,pixls);
      }
   else
      {
      draw_croi(kk,1,dysize,roi->xmin,roi->ymin,
                roi->radiusi,roi->radiusm,roi->radiuso,roi->col);
      show_pix8(kk,0,roi->xmin,roi->ymin,roi->xmin,roi->ymin,pixls);
      }
   goto sh_loop;
   }
}

/*

*/

/* ---- Clear Polyline on display bitmap ----------------------------- */

void polyclear(dspno,mem,xs,ys,np)

int    dspno, *xs, *ys, np;
MEM_DATA   *mem;

{
int     kindx, koff, hit;
int     *goff, *gx, *gy, *gcount, *gcol, *glw;
register int loopi, loopk;

GLIST   *gp;


gp = mem->gpntr;
if (gp == 0) return;

kindx = gp->geln;
if (kindx <= 0) return;

x = *xs;
dysize = ididev[dspno].ysize - 1;
y = dysize - (*ys);
hit = 0;


again:
goff = gp->off;
gcount = gp->count;
gcol = gp->color;
glw = gp->lwidth;

for (loopi=0; loopi<kindx; loopi++)
   {
   koff = *goff;
   gx = gp->x + koff;
   if (*gx == x) 
      {
      gy = gp->y + koff;
      if (*gy == y) 
         {
         if (gp->geln == 1)
            {
            gp->geln = 0;
            *gp->off = 0;
            }
         else
            {
            hit = 1;
            temp = loopi;
            goto clean_up;
            }
         }
      }
   goff ++; gcount ++; gcol ++; glw ++;
   }

if (hit == 1) polyrefr(dspno,mem,0,0);
return;


clean_up:
for (loopi=temp; loopi<(kindx-1); loopi++)
   {
   *gcount = *(gcount+1);
   *gcol = *(gcol+1);
   *glw = *(glw+1);

   for (loopk=0; loopk<(*gcount); loopk++)
      {
      *gx = *(gx+np);
      *gy = *(gy+np);
      gx ++; gy ++;
      }
   *(goff+1) = (*goff) + (*gcount);
   goff ++; gcount ++; gcol ++; glw ++;
   }

gp->geln --;
kindx = gp->geln;
goto again;                     /* there may be more */

}

/*

*/

/* ---- Clear Text on display bitmap ----------------------------- */

void txtclear(dspno,mem,xs,ys,np)

int    dspno, xs, ys, np;
MEM_DATA   *mem;

{
int     tindx, toff, hit, zoff;
register int loopi, loopk;

TLIST   *tp;


tp = mem->tpntr;
if (tp == (TLIST *)0) return;

tindx = tp->teln;
if (tindx <= 0) return;

x = xs;
dysize = ididev[dspno].ysize - 1;
y = dysize - ys;
hit = 0;
temp = 0;

again:
for (loopi=temp; loopi<tindx; loopi++)
   {
   if ((tp->x[loopi] == x) && (tp->y[loopi] == y))
      {
      if (tp->teln == 1)
         {
         tp->teln = 0;
         tp->off[0] = 0;
         }
      else
         {
         hit = 1;
         temp = loopi;
         goto clean_up;
         }
      }
   }

if (hit == 1) txtrefr(dspno,mem,0,0);
return;		


clean_up:
zoff = tp->off[temp+1];				/* offset of next element */
for (loopi=temp; loopi<(tindx-1); loopi++)
   {
   toff = tp->off[loopi];
   tp->count[loopi] = tp->count[loopi+1];
   tp->x[loopi] = tp->x[loopi+1];
   tp->y[loopi] = tp->y[loopi+1];
   tp->size[loopi] = tp->size[loopi+1];
   tp->color[loopi] = tp->color[loopi+1];

   for (loopk=0; loopk<tp->count[loopi+1]; loopk++)
      {
      tp->text[toff++] = tp->text[zoff++];
      }
   zoff = tp->off[loopi+2];		/* offset of [loop+1] in next loop */
   tp->off[loopi+1] = tp->off[loopi] + tp->count[loopi];
   }

tp->teln --;
tindx = tp->teln;
goto again;			/* there may be more */

}

/*

*/

/* ---- Copy graphics from overlay channel to image memory ----------- */

void copy_over(dspno,memid,append)
int  dspno, memid, append;

{
int  *x, *y, *off, *colo, *lw, *cou;
int  *ovx, *ovy, *ovoff, *ovcolo, *ovlw, *ovcou;
int  kk, kindx, ioff, coff;
register int  nr, mr;

char  *inpntr, *cpntr;

CONF_DATA  *conf;
MEM_DATA   *ovmem, *mem;
GLIST      *gpov, *gp;
TLIST   *tpov, *tp;


conf = ididev[dspno].confptr;
if (memid == conf->overlay) return;

mem = conf->memory[memid];
ovmem = conf->memory[conf->overlay];


/* work on the graphics */

gpov = ovmem->gpntr;
nr = gpov->geln;
if (nr == 0) goto text_section;		/* no graphics to copy */

gp = mem->gpntr;
if (append == 1)
   {
   kindx = gp->geln;
   gp->geln += gpov->geln;
   }
else
   {
   kindx = 0;
   gp->geln = gpov->geln;
   }

off = gp->off + kindx;
colo = gp->color + kindx;
lw = gp->lwidth + kindx;
cou = gp->count + kindx;
x = gp->x + kindx;
y = gp->y + kindx;

ovoff = gpov->off;
ovcolo = gpov->color;
ovlw = gpov->lwidth;
ovcou = gpov->count;
ovx = gpov->x;
ovy = gpov->y;

for (nr=0; nr<gpov->geln; nr++)
   {				/* copy offset, colour, linewidth, no_pnts */
   *off++ = *ovoff++;
   *colo++ = *ovcolo++;
   *lw++ = *ovlw++;
   *cou++ = *ovcou++;
   }
*off = *ovoff;			/* offset is 1 index farther... */

cou = gp->count + kindx;
for (nr=0; nr<gpov->geln; nr++)
   {				/* for each graph_elem copy x,y */
   for (mr=0; mr<(*cou); mr++)
      {
      *x++ = *ovx++;
      *y++ = *ovy++;
      }
   cou ++;
   }

polyrefr(dspno,mem,1,memid);


/* work on the text */

text_section:
tpov = ovmem->tpntr;
nr = tpov->teln;
if (nr == 0) return;		/* no text to copy */

tp = mem->tpntr;
if (append == 1)
   {
   kindx = tp->teln;
   tp->teln += tpov->teln;
   }
else
   {
   kindx = 0;
   tp->teln = tpov->teln;
   }

off = tp->off + kindx;
colo = tp->color + kindx;
lw = tp->size + kindx;
cou = tp->count + kindx;
x = tp->x + kindx;
y = tp->y + kindx;

ovoff = tpov->off;
ovcolo = tpov->color;
ovlw = tpov->size;
ovcou = tpov->count;
ovx = tpov->x;
ovy = tpov->y;

for (nr=0; nr<tpov->teln; nr++)
   {				/* copy offset, colour, size, no_pnts */
   *x++ = *ovx++;
   *y++ = *ovy++;
   *off++ = *ovoff++;
   *colo++ = *ovcolo++;
   *lw++ = *ovlw++;
   *cou++ = *ovcou++;
   }
*off = *ovoff;			/* offset is 1 index farther... */

coff = tp->off[kindx];
for (nr=0; nr<tpov->teln; nr++)
   {	
   ioff = tpov->off[nr];
   inpntr = &(tpov->text[ioff]);
   cpntr = &(tp->text[coff]);
   kk = tpov->count[nr];
   for (mr=0; mr<kk; mr++) *cpntr++ = *inpntr++;
   coff += kk;
   }

txtrefr(dspno,mem,1,memid);
}
