 /*
  * Khoros: $Id: collect.c,v 1.5 1992/03/20 22:47:23 dkhoros Exp $
  */

#if !defined(lint) && !defined(SABER)
static char rcsid[] = "Khoros: $Id: collect.c,v 1.5 1992/03/20 22:47:23 dkhoros Exp $";
#endif

 /*
  * $Log: collect.c,v $
 * Revision 1.5  1992/03/20  22:47:23  dkhoros
 * VirtualPatch5
 *
  */ 

/*
 *----------------------------------------------------------------------
 *
 * Copyright 1990, University of New Mexico.  All rights reserved.
 * 
 * Permission to copy and modify this software and its documen-
 * tation only for internal use in your organization is hereby
 * granted, provided that this notice is retained thereon and
 * on all copies.  UNM makes no representations as too the sui-
 * tability and operability of this software for any purpose.
 * It is provided "as is" without express or implied warranty.
 * 
 * UNM DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
 * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FIT-
 * NESS.  IN NO EVENT SHALL UNM BE LIABLE FOR ANY SPECIAL,
 * INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY OTHER DAMAGES WHAT-
 * SOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER
 * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
 * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PER-
 * FORMANCE OF THIS SOFTWARE.
 * 
 * No other rights, including for example, the right to redis-
 * tribute this software and its documentation or the right to
 * prepare derivative works, are granted unless specifically
 * provided in a separate license agreement.
 *----------------------------------------------------------------------
 */

#include "unmcopyright.h"	 /* Copyright 1990 by UNM */
#include "forms.h"

/* >>>>>>>>>>>>>>>>>>>>>>>>>>>>> <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
   >>>>                                                       <<<<
   >>>>		       file name: collect.c		      <<<<
   >>>>                                                       <<<<
   >>>>                Collection Routines                    <<<<
   >>>>                                                       <<<<
   >>>>	   These are the routines that actually collect data  <<<<
   >>>>    from parameter boxes on the forms (asciiString     <<<<
   >>>>    widgets) and store it in the internal database.    <<<<
   >>>>    In addition, the form tree is updated to show that <<<<
   >>>>    new information has been collected.                <<<<
   >>>>                                                       <<<<
   >>>> 	xvf_collect_check_data()		      <<<<
   >>>> 	xvf_collect_int()			      <<<<
   >>>> 	xvf_collect_float()			      <<<<
   >>>> 	xvf_collect_string()			      <<<<
   >>>> 	xvf_collect_infile()			      <<<<
   >>>> 	xvf_collect_outfile()			      <<<<
   >>>> 	xvf_update_form_tree()			      <<<<
   >>>>                                                       <<<<
   >>>>                                                       <<<<
   >>>>>>>>>>>>>>>>>>>>>>>>>>>>> <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<  */



/************************************************************
*
* Routine Name:  xvf_collect_check_data
*
*      Purpose:  This routine checks all of the asciiStringWidgets 
*		 on a particular pane to see if their inputs
*	   	 have changed.  AsciiStringWidgets are contained
*		 in InputFile, OutputFile, String, Integer, and
*		 Floats selections.  If any inputs have changed, 
*		 then the database is updated with the current value.
*
*        Input:  formptr - pointer to the form tree
*		 database - pointer to the internal database struct
*		 guideptr - pointer to the current guide 
*
*   Written By: Stephanie Hallett and Danielle Argiro
*
*************************************************************/

void xvf_collect_check_data(formptr, database, guideptr)
xvf_form *formptr;
char **database;
xvf_guide_button *guideptr;
{
   xvf_selection *current;
   int flag;

   /* 
    * go through the entire selection list on which this 
    * action button appears; collect any/all parameters of input files, 
    * output files, strings, integers, or floats that may have been 
    * changed and change their values at this time
    */ 

   if (guideptr == NULL)
      return;		/* no pane was selected */

   current = guideptr->pane->sel_list;

   while (current != NULL)
   {
      flag = xvf_get_line_type(database[current->index]);

      switch(flag) {

	  case InputFile:
	       xvf_collect_infile(formptr, database, current);
	       break;

	  case OutputFile:
	       xvf_collect_outfile(formptr, database, current);
               break;

          case IntegerOpt:
	       xvf_collect_int(formptr, database, current);
	       break;

          case FloatOpt:
	       xvf_collect_float(formptr, database, current);
	       break;

	  case StringOpt:
	       xvf_collect_string(formptr, database, current);
               break;

	  case AnswerInfile:
	       xvf_collect_ansinfile(formptr, database, current);
	       break;

	  case AnswerOutfile:
	       xvf_collect_ansoutfile(formptr, database, current);
	       break;

	  case Toggle:
	       xvf_collect_toggle(formptr, database, current);
	       break;
			    
          default:
	       break;

      } /* end switch */

      current = current->next;

   } /* end while */

}  /* end xvf_collect_check_data */



/************************************************************
*
* Routine Name:  xvf_collect_int
*
*      Purpose:  Called by xvf_collect_check_data, this routine
*		 collects the integer from the text widget, updates the 
*		 correct selection in the form tree, updates the int line
*		 in the database, etc.
*
*        Input:  formptr - pointer to the form tree
*		 database - pointer to the internal database struct
*		 current  - the current xvf_selection pointer
*
*   Written By: Stephanie Hallett and Danielle Argiro
*
*************************************************************/
	  
int xvf_collect_int(formptr, database, current)
xvf_form *formptr;
char **database;
xvf_selection *current;
{
	Line_Info line_info;
        int  i, tmp_int, check_int;
	char leftover[50], temp[512];
 	Arg  arg[MaxArgs];
	char *string_return;
	long id;


	/* get the string representing the integer from the ascii widget */
	i = 0;
	XtSetArg(arg[i], XtNstring, &string_return);	i++;
	XtGetValues(current->value_widget, arg, i); 
	current->buffer = string_return; 

	/* parse the integer line, to get valid line_info struct */
	xvf_clear_line_info(&line_info);
	xvf_parse_int_line(database[current->index], &line_info);

	/* see if it's not a regular integer (ie, an expression) */
	if (sscanf(current->buffer,"%d%s",&tmp_int,leftover) != 1)
	{
	    /* can't scan it normally - try to evaluate expression */
	    id = (long) formptr; /* this is the id for this form */
	    if (XVF_EXPRESSION == false)
	    {
	       sprintf(temp,"Error: '%s' %s\n is not a proper integer\n",
		       line_info.title, line_info.literal);
               xvf_error_wait(temp, "Check_Data", NULL);
	       FORM_DONE = false;
               return(NULL);
	    }
	    else if (!(xve_eval_int(id, current->buffer, &tmp_int, NULL))) 
	    {
	        FORM_DONE = false;
		line_info.literal = xvf_strcpy(current->buffer);
	        xvf_deparse_int_line(&line_info, database, current->index);
	        return(false);
	    }
	    else
	    {
	       	line_info.int_val = tmp_int;
		line_info.literal = xvf_strcpy(current->buffer);
	        current->modified = true;
	        current->selected = true;
	        xvf_deparse_int_line(&line_info, database, current->index);
	    }
	}

        /* it can be scanned into a normal int field - error check bounds */
	else
	{
	    if (line_info.int_val != tmp_int)
	    {
	       check_int = check_bounds_int(tmp_int, line_info.upper_int,
		                            line_info.lower_int);
	       switch(check_int) 
	       {
	          case -3: 
			sprintf(temp, "Invalid integer '%d' for '%s' (%s).  Integer value must be < 0; please re-enter", tmp_int, 
				line_info.title, line_info.variable);
                      	xvf_error_wait(temp, "Check data",NULL);
	  	        FORM_DONE = false;
	                return(false);
		        break;

		  case -2: 
			sprintf(temp, "Invalid integer '%d' for '%s' (%s).  Integer value must be <= 0; please re-enter", tmp_int, 
                                line_info.title, line_info.variable);
                       	xvf_error_wait(temp, "Check data",NULL);
	  	        FORM_DONE = false;
	                return(false);
                        break;

	 	 case  -1: 
			sprintf(temp, "Invalid integer '%d' for '%s' (%s). Integer value must be greater than %d, less than %d; please reenter", tmp_int, 
		         	line_info.title, line_info.variable, 
				line_info.lower_int, line_info.upper_int);
                       	xvf_error_wait(temp, "Check data",NULL);
	  	        FORM_DONE = false;
	                return(false);
                       	break;

		 case  1: 
			sprintf(temp, "Invalid integer '%d' for '%s' (%s).  Integer value must be >= 0; please re-enter", tmp_int, line_info.title, 
				line_info.variable);
                       	xvf_error_wait(temp, "Check data",NULL);
	  	        FORM_DONE = false;
	                return(false);
                       	break;

		 case  2:
			sprintf(temp, "Invalid integer '%d' for '%s' (%s).  Integer value must be > 0; please re-enter", tmp_int, line_info.title, 
				line_info.variable);
                       	xvf_error_wait(temp, "Check data",NULL);
	  	        FORM_DONE = false;
	                return(false);
                       	break;

		 case  0:
	        	line_info.int_val = tmp_int;
			line_info.literal = xvf_strcpy(current->buffer);
	                current->modified = true;
	                current->selected = true;
	       	        xvf_deparse_int_line(&line_info, database, 
					     current->index);
	                return(true);
		 	break;

                default:
			fprintf(stderr, "xvf_collect_int:\n");
			fprintf(stderr, "  ERROR: bad status returned from\n");
			fprintf(stderr, "         check_bounds_int\n");
	                return(false);
			break;
                    }  /* end switch */
	    } /* end if */
        } /* end else */
	return(true);
}

/************************************************************
*
* Routine Name:  xvf_collect_float
*
*      Purpose:  Called by xvf_collect_check_data, this routine
*		 collects the float from the text widget, updates the 
*		 correct selection in the form tree, updates the float line
*		 in the database, etc.
*
*        Input:  formptr - pointer to the form tree
*                database - pointer to the internal database struct
*                current  - the current xvf_selection pointer
*
*   Written By: Stephanie Hallett and Danielle Argiro
*
*************************************************************/
	  
int xvf_collect_float(formptr, database, current)
xvf_form *formptr;
char **database;
xvf_selection *current;
{
	Line_Info line_info;
        int   i, check_float;
	char  leftover[50], temp[512];
	float tmp_float;
	double atof(); 
 	Arg   arg[MaxArgs];
	char  *string_return, *digits;
	long id;

	/* get the string representing the float from the ascii widget */
	i = 0;
	XtSetArg(arg[i], XtNstring, &string_return);	i++;
	XtGetValues(current->value_widget, arg, i); 
	current->buffer = string_return; 

	/* parse the integer line, to get valid line_info struct */
	xvf_clear_line_info(&line_info);
	xvf_parse_float_line(database[current->index], &line_info);

	/* see if it's not a regular float (ie, could be an expression) */
	if (sscanf(current->buffer,"%f%s",&tmp_float,leftover) != 1)
	{
	    /* can't scan it normally - try to evaluate expression */
	    id = (long) formptr; /* this is the id for this form */
	    if (XVF_EXPRESSION == false)
	    {
	       sprintf(temp,"Error: '%s' %s\n is not a proper float\n",
		       line_info.title, line_info.literal);
               xvf_error_wait(temp, "Check_Data", NULL);
	       FORM_DONE = false;
               return(NULL);
	    }
	    else if (!(xve_eval_float(id, current->buffer, &tmp_float, NULL))) 
	    {
	        FORM_DONE = false;
		line_info.literal = xvf_strcpy(current->buffer);
	        xvf_deparse_float_line(&line_info, database, current->index);
	        return(false);
	    }
	    else
	    {
	       	line_info.float_val = tmp_float;
		line_info.literal = xvf_strcpy(current->buffer);
	        current->modified = true;
	        current->selected = true;
	        xvf_deparse_float_line(&line_info, database, current->index);
	    }
	}

	/* it can be scanned into a normal float field - error check bounds */
	else
	{
	    if (line_info.float_val != tmp_float)
	    {
	        check_float = check_bounds_float(tmp_float, 
				                 line_info.upper_float,
		                                 line_info.lower_float);
	        switch(check_float) 
	        {
		    case -3: 
			sprintf(temp, 
			"Invalid float '%g' for '%s' (%s).  Float value must be < 0.0; please re-enter", tmp_float, line_info.title, line_info.variable);
                      	xvf_error_wait(temp, "Check data",NULL);
		        FORM_DONE = false;
	                return(false);
		        break;

		    case -2: 
			sprintf(temp, "Invalid float '%g' for '%s' (%s).  Float value must be <= 0.0; please re-enter", tmp_float, line_info.title, line_info.variable);
                       	xvf_error_wait(temp, "Check data",NULL);
		        FORM_DONE = false;
	                return(false);
                        break;

		   case  -1: 
			sprintf(temp, "Invalid float '%g' for '%s' (%s).  Float value must be greater than %g, less than %g; please reenter", tmp_float,  line_info.title, line_info.variable, line_info.lower_float, line_info.upper_float);
                       	xvf_error_wait(temp, "Check data",NULL);
		        FORM_DONE = false;
	                return(false);
                      	break;

		   case  1: 
			sprintf(temp, "Invalid float '%g' for '%s' (%s).  Float value must be >= 0.0; please re-enter", tmp_float, line_info.title, line_info.variable);
                       	xvf_error_wait(temp, "Check data",NULL);
		        FORM_DONE = false;
	                return(false);
                       	break;

		   case  2:
			sprintf(temp, "Invalid float '%g' for '%s' (%s).  Float value must be > 0.0; please re-enter", tmp_float, line_info.title, line_info.variable);
                        xvf_error_wait(temp, "Check data",NULL);
		        FORM_DONE = false;
	                return(false);
                       	break;

		   case  0:
		       	line_info.float_val = tmp_float;
			line_info.literal = xvf_strcpy(current->buffer);
		        current->modified = true;
		        current->selected = true;
	                xvf_deparse_float_line(&line_info, database, 
					       current->index);
	                return(true);
		 	break;

                  default:
			fprintf(stderr, "xvf_collect_float:\n");
			fprintf(stderr, "  ERROR: bad status returned from\n");
			fprintf(stderr, "         check_bounds_float\n");
	                return(false);
			break;
                  } /* end switch */
               } /* end if */
 	} /* end else */
	return(true);
}


/************************************************************
*
* Routine Name:  xvf_collect_infile
*
*      Purpose:  Called by xvf_collect_check_data, this routine
*		 collects the input filename from the text widget, updates the 
*		 correct selection in the form tree, updates the inputfile line
*		 in the database, etc.
*
*        Input:  formptr - pointer to the form tree
*                database - pointer to the internal database struct
*                current  - the current xvf_selection pointer
*
*   Written By: Stephanie Hallett and Danielle Argiro
*
*************************************************************/

xvf_collect_infile(formptr, database, current)
xvf_form *formptr;
char **database;
xvf_selection *current;
{
	Line_Info line_info;
	char leftover[50], temp[MaxLength];
        char tmp_file[MaxLength], buffer[MaxLength];
 	Arg  arg[MaxArgs];
	int  i, j;
	char *string_return, *filename;
	long id;

	/* get the string representing the filename from the ascii widget */
	i = 0;
	XtSetArg(arg[i], XtNstring, &string_return);	i++;
	XtGetValues(current->value_widget, arg, i);
  	current->buffer = string_return; 

	/* parse the infile line, to get valid line_info struct */
	xvf_clear_line_info(&line_info);
	xvf_parse_input_line(database[current->index], &line_info);

	/* any spaces, etc in filename ? print error message & return */
        if (sscanf(current->buffer,"%s%s",tmp_file,leftover) > 1)
        { 
	    sprintf(temp,"XVForm Error: '%s' %s is not a proper filename\n",
	            line_info.title,current->buffer);
	    xvf_error_wait(temp, "Check_Data", NULL);
	    FORM_DONE = false;
	    return(false);
        }

	/* try to parse an expression - if parser fails, return failure */
        else
        {
	    /* can't scan it normally - try to evaluate expression */
	    id = (long) formptr; /* this is the id for this form */
	    if (XVF_EXPRESSION == false)
	    {
		strcpy(tmp_file, current->buffer);
	    }
	    else 
	    {
		buffer[0] = '\0';
		i = 0; j = 0;
		while (current->buffer[i] != '\0')
		{
		    if ((current->buffer[i] != ' ' ) && 
		        (current->buffer[i] != '\t') &&
		        (current->buffer[i] != '\n'))
		    {
			buffer[j] = current->buffer[i]; i++; j++;
		    }
		    else  i++;
		}
		buffer[j] = '\0';
		
	        if (VStrcmp(buffer, "")!=0)
	    	    filename = vfullpath(buffer, NULL, NULL);
	        else
	    	    filename = xvf_strcpy("");
	        if (!(xve_eval_string(id, filename, tmp_file, NULL))) 
	        {
		    line_info.filename= xvf_strcpy(current->buffer);
		    line_info.literal = xvf_strcpy(current->buffer);
	            current->modified = true;
	            xvf_deparse_input_line(&line_info,database,current->index);
	            return(false);
	        }
	    }
            if (line_info.filename != NULL)
            {
 	       /* need to check to see if file changed */
                if (VStrcmp(line_info.filename, tmp_file) != 0)
	  	{
	            line_info.filename = xvf_strcpy(tmp_file);
	            line_info.literal = xvf_strcpy(current->buffer);
	            current->selected = true;
 	            current->modified = true;
	   	}
	    }
	    else if (xvf_strlen(tmp_file) > 0)
	    {
		line_info.filename = xvf_strcpy(tmp_file);
                line_info.literal = xvf_strcpy(current->buffer);
                current->selected = true;
                current->modified = true;
	    }
            xvf_deparse_input_line(&line_info, database, current->index);
       }
       tmp_file[0] = '\0';
       return(true);
}


/************************************************************
*
* Routine Name:  xvf_collect_ansinfile
*
*      Purpose:  Called by xvf_collect_check_data, this routine
*		 collects the Answer Infile from text widget, updates the 
*		 correct selection in the form tree, updates the Answer
*		 Infile line in the UIS, etc.
*
*        Input:  formptr - pointer to the form tree
*                database - pointer to the internal database struct
*                current  - the current xvf_selection pointer
*
*   Written By: Danielle Argiro
*
*************************************************************/

xvf_collect_ansinfile(formptr, database, current)
xvf_form *formptr;
char **database;
xvf_selection *current;
{
	Line_Info line_info;
	char leftover[50], temp[MaxLength];
        char tmp_file[MaxLength], buffer[MaxLength];
 	Arg  arg[MaxArgs];
	int  i, j;
	char *string_return, *filename;
	long id;

	/* get the string representing the filename from the ascii widget */
	i = 0;
	XtSetArg(arg[i], XtNstring, &string_return);	i++;
	XtGetValues(current->value_widget, arg, i);
  	current->buffer = string_return; 

	/* parse the infile line, to get valid line_info struct */
	xvf_clear_line_info(&line_info);
	xvf_parse_ansinfile_line(database[current->index], &line_info);

	/* any spaces, etc in filename ? print error message & return */
        if (sscanf(current->buffer,"%s%s",tmp_file,leftover) > 1)
        { 
	    sprintf(temp,"XVForm Error: '%s' %s is not a proper filename\n",
	            line_info.title,current->buffer);
	    xvf_error_wait(temp, "Check_Data", NULL);
	    FORM_DONE = false;
	    return(false);
        }

	/* try to parse an expression - if parser fails, return failure */
        else
        {
	    /* can't scan it normally - try to evaluate expression */
	    id = (long) formptr; /* this is the id for this form */
	    if (XVF_EXPRESSION == false)
	    {
		strcpy(tmp_file, current->buffer);
	    }
	    else 
	    {
		buffer[0] = '\0';
		i = 0; j = 0;
		while (current->buffer[i] != '\0')
		{
		    if ((current->buffer[i] != ' ' ) && 
		        (current->buffer[i] != '\t') &&
		        (current->buffer[i] != '\n'))
		    {
			buffer[j] = current->buffer[i]; i++; j++;
		    }
		    else  i++;
		}
		buffer[j] = '\0';
		
	        if (VStrcmp(buffer, "")!=0)
	    	    filename = vfullpath(buffer, NULL, NULL);
	        else
	    	    filename = xvf_strcpy("");
	        if (!(xve_eval_string(id, filename, tmp_file, NULL))) 
	        {
		    line_info.filename= xvf_strcpy(current->buffer);
		    line_info.literal = xvf_strcpy(current->buffer);
	            current->modified = true;
	            xvf_deparse_ansinfile_line(&line_info,
					       database,current->index);
	            return(false);
	        }
	    }
            if (line_info.filename != NULL)
            {
 	       /* need to check to see if file changed */
                if (VStrcmp(line_info.filename, tmp_file) != 0)
	  	{
	            line_info.filename = xvf_strcpy(tmp_file);
	            line_info.literal = xvf_strcpy(current->buffer);
	            current->selected = true;
 	            current->modified = true;
	   	}
	    }
	    else if (xvf_strlen(tmp_file) > 0)
	    {
		line_info.filename = xvf_strcpy(tmp_file);
                line_info.literal = xvf_strcpy(current->buffer);
                current->selected = true;
                current->modified = true;
	    }
            xvf_deparse_ansinfile_line(&line_info, database, current->index);
       }
       tmp_file[0] = '\0';
       return(true);
}

/************************************************************
*
* Routine Name:  xvf_collect_outfile
*
*      Purpose:  Called by xvf_collect_check_data, this routine
*		 collects the output filename from the text widget, 
*		 updates the correct selection in the form tree, 
*		 updates the outputfile line in the database, etc.
*
*        Input:  formptr - pointer to the form tree
*                database - pointer to the internal database struct
*                current  - the current xvf_selection pointer
*
*   Written By: Stephanie Hallett and Danielle Argiro
*
*************************************************************/

xvf_collect_outfile(formptr, database, current)
xvf_form *formptr;
char **database;
xvf_selection *current;
{
	Line_Info line_info;
	char leftover[50], temp[MaxLength]; 
	char buffer[MaxLength], tmp_file[MaxLength];
 	Arg  arg[MaxArgs];
	int  i, j;
	char *string_return, *filename;
	long id;

	/* get the string representing the filename from the ascii widget */
	i = 0;
	XtSetArg(arg[i], XtNstring, &string_return);	i++;
	XtGetValues(current->value_widget, arg, i);
  	current->buffer = string_return; 

	/* parse the integer line, to get valid line_info struct */
	xvf_clear_line_info(&line_info);
	xvf_parse_output_line(database[current->index], &line_info);

        if (sscanf(current->buffer,"%s%s",tmp_file,leftover) > 1)
	{
	    sprintf(temp,"XVForm Error: '%s' %s is not a proper filename\n", 
		    line_info.title,current->buffer);

	    xvf_error_wait(temp, "Check_Data", NULL);
	    FORM_DONE = false;
	    return(false);
	}

	/* try to parse an expression - if parser fails, return failure */
	else
	{
	    id = (long) formptr; /* this is the id for this form */

	    /* can't scan it normally - try to evaluate expression */
	    if (XVF_EXPRESSION == false)
	    {
	       strcpy(tmp_file, current->buffer);
	    }
	    else 
	    {
		buffer[0] = '\0';
                i = 0; j = 0;
                while (current->buffer[i] != '\0')
                {
                    if ((current->buffer[i] != ' ' ) &&
                        (current->buffer[i] != '\t') &&
                        (current->buffer[i] != '\n'))
                    {
                        buffer[j] = current->buffer[i]; i++; j++;
                    }
                    else  i++;
                }
                buffer[j] = '\0';

                if (VStrcmp(buffer, "")!=0)
                    filename = vfullpath(buffer, NULL, NULL);
                else
                    filename = xvf_strcpy("");

		if (!(xve_eval_string(id, filename, tmp_file, NULL))) 
	        {
		    line_info.filename = xvf_strcpy(current->buffer);
		    line_info.literal = xvf_strcpy(current->buffer);
		    current->modified = true;
	            xvf_deparse_output_line(&line_info,database,current->index);
	            return(false);
	        }
	    }
	    if (line_info.filename != NULL)
	    {
	        /* need to check to see if filename changed */
	        if (VStrcmp(line_info.filename, tmp_file) != 0)
		{
		    line_info.filename = xvf_strcpy(tmp_file);
                    line_info.literal = xvf_strcpy(current->buffer);
                    current->selected = true;
		    current->modified = true;
		}
	    }
	    else if (xvf_strlen(tmp_file) > 0)
	    {
	 	line_info.filename = xvf_strcpy(tmp_file);
                line_info.literal = xvf_strcpy(current->buffer);
                current->selected = true;
                current->modified = true;

            }
	    xvf_deparse_output_line(&line_info, database, current->index);
	}
	tmp_file[0] = '\0';
	return(true);
}

/************************************************************
*
* Routine Name:  xvf_collect_ansoutfile
*
*      Purpose:  Called by xvf_collect_check_data, this routine
*		 collects the Answer Outfile name from the text widget, 
*		 updates the correct selection in the form tree, 
*		 updates the outputfile line in the database, etc.
*
*        Input:  formptr - pointer to the form tree
*                database - pointer to the internal database struct
*                current  - the current xvf_selection pointer
*
*   Written By: Danielle Argiro
*
*************************************************************/

xvf_collect_ansoutfile(formptr, database, current)
xvf_form *formptr;
char **database;
xvf_selection *current;
{
	Line_Info line_info;
	char leftover[50], temp[MaxLength]; 
	char buffer[MaxLength], tmp_file[MaxLength];
 	Arg  arg[MaxArgs];
	int  i, j;
	char *string_return, *filename;
	long id;

	/* get the string representing the filename from the ascii widget */
	i = 0;
	XtSetArg(arg[i], XtNstring, &string_return);	i++;
	XtGetValues(current->value_widget, arg, i);
  	current->buffer = string_return; 

	/* parse the integer line, to get valid line_info struct */
	xvf_clear_line_info(&line_info);
	xvf_parse_ansoutfile_line(database[current->index], &line_info);

        if (sscanf(current->buffer,"%s%s",tmp_file,leftover) > 1)
	{
	    sprintf(temp,"XVForm Error: '%s' %s is not a proper filename\n", 
		    line_info.title,current->buffer);

	    xvf_error_wait(temp, "Check_Data", NULL);
	    FORM_DONE = false;
	    return(false);
	}

	/* try to parse an expression - if parser fails, return failure */
	else
	{
	    id = (long) formptr; /* this is the id for this form */

	    /* can't scan it normally - try to evaluate expression */
	    if (XVF_EXPRESSION == false)
	    {
	       strcpy(tmp_file, current->buffer);
	    }
	    else 
	    {
		buffer[0] = '\0';
                i = 0; j = 0;
                while (current->buffer[i] != '\0')
                {
                    if ((current->buffer[i] != ' ' ) &&
                        (current->buffer[i] != '\t') &&
                        (current->buffer[i] != '\n'))
                    {
                        buffer[j] = current->buffer[i]; i++; j++;
                    }
                    else  i++;
                }
                buffer[j] = '\0';

                if (VStrcmp(buffer, "")!=0)
                    filename = vfullpath(buffer, NULL, NULL);
                else
                    filename = xvf_strcpy("");

		if (!(xve_eval_string(id, filename, tmp_file, NULL))) 
	        {
		    line_info.filename = xvf_strcpy(current->buffer);
		    line_info.literal = xvf_strcpy(current->buffer);
		    current->modified = true;
	            xvf_deparse_output_line(&line_info,database,current->index);
	            return(false);
	        }
	    }
	    if (line_info.filename != NULL)
	    {
	        /* need to check to see if filename changed */
	        if (VStrcmp(line_info.filename, tmp_file) != 0)
		{
		    line_info.filename = xvf_strcpy(tmp_file);
                    line_info.literal = xvf_strcpy(current->buffer);
                    current->selected = true;
		    current->modified = true;
		}
	    }
	    else if (xvf_strlen(tmp_file) > 0)
	    {
	 	line_info.filename = xvf_strcpy(tmp_file);
                line_info.literal = xvf_strcpy(current->buffer);
                current->selected = true;
                current->modified = true;

            }
	    xvf_deparse_ansoutfile_line(&line_info,database,current->index);
	}
	tmp_file[0] = '\0';
	return(true);
}

/************************************************************
*
* Routine Name:  xvf_collect_string
*
*      Purpose:  Called by xvf_collect_check_data, this routine
*		 collects the string from the text widget, 
*		 updates the correct selection in the form tree, 
*		 updates the string line in the database, etc.
*
*        Input:  formptr - pointer to the form tree
*                database - pointer to the internal database struct
*                current  - the current xvf_selection pointer
*
*   Written By: Stephanie Hallett and Danielle Argiro
*
*************************************************************/

xvf_collect_string(formptr, database, current)
xvf_form *formptr;
char **database;
xvf_selection *current;
{
	Line_Info line_info;
 	Arg  arg[MaxArgs];
	int  i;
	char *string_return;
	char tmp_string[20*MaxLength];
	long id;

	i = 0;
	XtSetArg(arg[i], XtNstring, &string_return);	i++;
	XtGetValues(current->value_widget, arg, i);
  	current->buffer = string_return; 
	sprintf(tmp_string, "%s", string_return);

	/* parse the string line, to get valid line_info struct */
	xvf_clear_line_info(&line_info);
	xvf_parse_string_line(database[current->index], &line_info);

        id = (long) formptr; /* this is the id for this form */
	if (XVF_EXPRESSION == false)
	{
	   strcpy(tmp_string, current->buffer);
	}
        else if (!(xve_eval_string(id, current->buffer, tmp_string, NULL))) 
        {
	    FORM_DONE = false;
	    line_info.filename= xvf_strcpy(current->buffer);
	    line_info.literal = xvf_strcpy(current->buffer);
	    xvf_deparse_string_line(&line_info, database, current->index);
	    return(false);
        }

        line_info.literal = xvf_strcpy(current->buffer);

	if (line_info.string_val != NULL)
	{
	    if (VStrcmp(line_info.string_val, tmp_string) != 0)
	    {
	        line_info.string_val = xvf_strcpy(tmp_string);
		line_info.literal = xvf_strcpy(current->buffer);
	        current->selected = true;
	        current->modified = true;
	     }
        }
        else if (xvf_strlen(tmp_string) > 0)
        {
	     line_info.string_val = xvf_strcpy(tmp_string);
             line_info.literal = xvf_strcpy(current->buffer);
             current->selected = true;
             current->modified = true;
        }
	xvf_deparse_string_line(&line_info, database, current->index);
	return(true);
}

/************************************************************
*
* Routine Name:  xvf_collect_toggle
*
*      Purpose:  Called by xvf_collect_check_data, this routine
*		 collects the number of the toggle item selected
*
*        Input:  formptr - pointer to the form tree
*		 database - pointer to the internal database struct
*		 current  - the current xvf_selection pointer
*
*   Written By: Danielle Argiro
*
*************************************************************/

xvf_collect_toggle(formptr, database, current)
xvf_form *formptr;
char **database;
xvf_selection *current;
{
	xvf_selection *selection;
	Line_Info line_info, tmp_line_info;
	int count = 0;

	xvf_clear_line_info(&line_info);
	xvf_clear_line_info(&tmp_line_info);

	xvf_parse_toggle_line(database[current->index], &line_info);
	selection = current->toggle_next;

	while (selection != NULL)
	{
	    count++;
	    xvf_gen_parse(database[selection->index], &tmp_line_info);
	    if (tmp_line_info.opt_sel == true) break;
	    selection = selection->next;
	}
	line_info.toggle_val = count;
	xvf_deparse_toggle_line(&line_info, database, current->index);
}


/************************************************************
*
* Routine Name:  xvf_update_form_tree
*
*      Purpose:  Called by many of the callback routines, this routine
*		 updates the form tree, before xvf_collect_check_data
*		 is called.
*
*        Input:  database - pointer to the internal database struct
*		 index    - index of the current selection
*		 subformptr - pointer to the current subform 
*
*   Written By: Stephanie Hallett and Danielle Argiro
*
*************************************************************/
	  
xvf_update_form_tree(database, index, subformptr)
char **database;
int  index;
xvf_sub_form *subformptr;
{

   int       flag, pane_index;
   Line_Info line_info;
   xvf_guide_button *guide;

   /* set this line in the database to be selected */
   xvf_clear_line_info(&line_info);

   /* get the index of the appropriate StartPane line */
   flag = 0;
   while (flag != StartPane)
   {
	index --;
	flag = xvf_get_line_type(database[index]);
   } 
   pane_index = index;

  /* update the Pane line of the database */
  xvf_clear_line_info(&line_info);
  xvf_parse_startpane_line(database[pane_index], &line_info);
  line_info.selected = true;
  xvf_deparse_startpane_line(&line_info, database, pane_index);

   /* look for the right guide button to turn on, turn the old one off */
   guide = subformptr->guide_button; 
   while (guide != NULL)
   {
	/* 2 checks:  before trying to turn the right guide button on,
	              and the old one off
	          1 - make sure that we need to do this at all - only if there
		      is a pane associated with the guide button and 
		      it is a "true" guide button
		  2 - make sure that a guide button exists at all -
		      if there was only one pane on the form, and therefore
		      no guide buttons, the guide index will be -1
	*/
	if ((guide->pane != NULL) && (guide->index != -1))
	{
	   if (guide->pane->index == pane_index)
	   {
		guide->selected = true;

   		xvf_clear_line_info(&line_info);
		xvf_parse_guide_line(database[guide->index], &line_info);
		line_info.selected = true;
		xvf_deparse_guide_line(&line_info, database, guide->index);

	   }
	  else 
	  {
		guide->selected = false;

   		xvf_clear_line_info(&line_info);
		xvf_parse_guide_line(database[guide->index], &line_info);
		line_info.selected = false;
		xvf_deparse_guide_line(&line_info, database, guide->index);

   		xvf_clear_line_info(&line_info);
		xvf_parse_startpane_line(database[guide->pane->index], 
					 &line_info);
		line_info.selected = false;
		xvf_deparse_startpane_line(&line_info, database, guide->pane->index);
	 }
       }
       guide = guide->next_button;
   }

}

