/*===========================================================================
  Copyright (C) 1995-2009 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
===========================================================================*/

/*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
.IDENTIFIER  SKIPNUL
.AUTHOR      R.M. van Hees IPG-ESO Garching
.KEYWORDS    plot software, 3-D tables
.LANGUAGE    C
.PURPOSE     skip null values not along a vector, but in opposite direction
             in both vectors or planes
      input: int   nline[2]  dimension of the second axis of both planes.
                             This are the number of points connected by a line,
                             or with the same symbol in the plot table routines
             int   *inull[2] array with NULL flags for both planes
             float *inoutval[2] array with the data of both planes

  in/output: int   *nconn    dimension of the first axis of both planes.
                             Note that the number of points along this axis
                             has to be equal for both planes
             
     output: int   *nnull    number of NULL values found

.COMMENTS    this routine has a different effect on the data (if it contains
             NULL values) than using one of the tbl_readplaneXX routines with
             NULL flag is ON. The tbl_readplaneXX routines reject vectors 
             (lines) from a plane, while this routine removes all values
             at a certain position along the first axes in BOTH planes.

.ENVIRONment MIDAS and AGL
             #include <midas_def.h>     Prototypes for MIDAS interfaces
             #include <plot_def.h>      Symbols used by the PLT interfaces

 also holds routine getColor

.VERSION     1.1     19-Dec-1993   added parameter # NULL values found

 090422		last modif
------------------------------------------------------------*/
  
#define  _POSIX_SOURCE 1

/*
 * definition of the used functions in this module
 */

#include <stdlib.h>

#include <midas_def.h>

/*
 * define some macros and constants
 */
#include <plot_def.h>

/*
 * here start the code of the routine
 */
void SKIPNULL( nline, inull, inoutval, nconn, nnull)
int   nline[2], *inull[2], *nconn, *nnull;
float *inoutval[2];

{
int    *not_null, *p_null;
float  *pntr1, *pntr2;

register int ii, nc, nl, num_null;

/*
 * initialize the number of NULL values found
 */
num_null = 0;
not_null = (int *) osmmget( *nconn * sizeof(int) );
for ( nc = 0; nc < *nconn; nc++ ) not_null[nc] = TRUE;

/*
 * hunt for NULL values...
 */
for ( ii = 0; ii < PLDIM2; ii++ )
    { p_null = inull[ii];
      for ( nl = 0; nl < nline[ii]; nl++ )
          { for ( nc = 0; nc < *nconn; nc++ )
                { if ( *p_null++ && not_null[nc] ) 
                     { not_null[nc] = FALSE;
                       num_null++;
                     }
                }
          }
    }


/*
 * reject the data with NULL values
 */

if (num_null != 0) 
   {
   for ( ii = 0; ii < PLDIM2; ii++ )
      { 
      pntr2 = pntr1 = inoutval[ii];
      for ( nl = 0; nl < nline[ii]; nl++ )
         {
         for ( nc = 0; nc < *nconn; nc++ )
            if ( not_null[nc] ) *pntr2++ = *(pntr1+nc);
         pntr1 += *nconn;
         }
      }

   *nnull  = num_null;
   *nconn -= num_null;
   }
else
   *nnull = 0;

(void) osmmfree( (char *) not_null );
}
/*

*/

void  getColor(colspecs,icol1,icol2)
char  *colspecs;
int   *icol1, *icol2;

{
char  tmp[24];

int  m;




*icol1 = *icol2 = -1;		/* default to invalid colours */
 
(void) strncpy(tmp,colspecs,23);
tmp[23] = '\0';

m = CGN_INDEXC(tmp,',');
if (m < 1)
   {
   *icol1 = ColNo(tmp);
   }
else
   {
   tmp[m] = '\0';
   *icol1 = ColNo(tmp);
   *icol2 = ColNo(tmp+m+1);
   }
} 





int ColNo(buf)
char  *buf;

{
register char cr;

int  icol;


icol = -1;

if ((*buf >= '0') && (*buf < '9'))
   {
   icol = atoi(buf);            /* colour no. explicitly given */
   if ((icol < 0) || (icol > 8)) icol = -1;
   }
else
   {
   CGN_UPSTR(buf);
   cr = buf[0];

   if (cr == 'R')
      icol = 2;			/* red */
   else if (cr == 'G')
      icol = 3;			/* green */
   else if (cr == 'Y')
      icol = 5;			/* yellow */
   else if (cr == 'M')
      icol = 6;			/* magenta */
   else if (cr == 'C')
      icol = 7;			/* cyan */
   else if (cr == 'W')
      icol = 8;			/* white */
   else if (cr == 'B')
      {
      cr = buf[1];
      if (cr == 'A')
         icol = 0;		/* background */
      else if (cr == 'L')
         {
         cr = buf[2];
         if (cr == 'U')
            icol = 4;		/* blue */
         else
            icol = 1;		/* black */
         }
      }
   }

return icol;
}
/*

*/

void SSKIPNULL( nline, inull, inoutval, nconn, nnull, sele )
int   nline[2], *inull[2], *nconn, *nnull, *sele;
float *inoutval[2];

{
int    *not_null, *p_null;
float  *pntr1, *pntr2;

register int ii, nc, nl, num_null;

/*
 * initialize the number of NULL values found
 */

num_null = 0;
not_null = (int *) osmmget( *nconn * sizeof(int) );
for ( nc = 0; nc < *nconn; nc++ ) not_null[nc] = TRUE;

/*
 * hunt for NULL values...
 */

for ( ii = 0; ii < PLDIM2; ii++ )
    { p_null = inull[ii];
      for ( nl = 0; nl < nline[ii]; nl++ )
          { for ( nc = 0; nc < *nconn; nc++ )
                { if ( *p_null++ && not_null[nc] ) 
                     { not_null[nc] = FALSE;
                       num_null++;
                     }
                }
          }
    }

/*
 * reject the data with NULL values
 */

if (num_null != 0) 
   {
   for ( ii = 0; ii < PLDIM2; ii++ )
      {
      pntr2 = pntr1 = inoutval[ii];

      for ( nl = 0; nl < nline[ii]; nl++ )
         {
         for ( nc = 0; nc < *nconn; nc++ )
            {
            if ( not_null[nc] )
               {
               *pntr2++ = *(pntr1+nc);
               }
            }
         pntr1 += *nconn;
         }
      }

   /* also update the selection flags accordingly */

   p_null = sele;
   for (nc=0; nc<*nconn; nc++)		/* use original no. of points */
      {
      if (not_null[nc])
         {
         *p_null++ = *(sele+nc);
         }
      }

   *nnull  = num_null;
   *nconn -= num_null;
   }
else
   *nnull = 0;


(void) osmmfree( (char *) not_null );
}
 
