#ifndef FLAG_HPP
#define FLAG_HPP

/****************************************************************************\
 
                         Copyright (C) 1991
                         Joe Kleinwaechter

      This file remains the property of Joe Kleinwaechter and may be
      used freely at no charge. It may not however be resold by anyone or
      included in a Class Library package without my written consent.



 File:         arg.hpp
 
 Description:  This is the header file for those that wish to wish to use
               the command line parmeters class - arg.

 Usage:        The command line parameters class 'arg' is used to be able to
               quickly parse off command line switches in a non-order dependent
               manner. The command line parsed is of the form:

               c:>progname +s -q +tHello name

               where:
                  progname is the name of the program.
                  +n is an nonvalued switch, of label 'n', that has been SET
                  -n is an nonvalued switch, of label 'n', that has been CLEARED
                  +nVALUE is a valued switch of label 'n', that has been SET
                           and has 'VALUE' as its associated text.
                  -nVALUE is a valued switch of label 'n', that has been CLEARED
                           and has 'VALUE' as its associated text.
                  name is an unlabeled switch having 'NAME' as its associated
                           text.

 Example:      #include <stream.hpp>
               #include "arg.hpp"

               main(int argc, char *argv[])
               {
(1)            arg parm(argc,argv,1);
(2)            char value[80];
               argState status;
               
(3)               argState = parm.isSet('t',value);

                  if (status == ARG_NOT_SPECIFIED)
                     cout << "t switch was not specified";
                  else if (status == ARG_CLEAR)
                     {
                     cout << "t switch had a leading - ";
                     cout << "with a value of " << value;
                     }
                  else if (status == ARG_SET)
                     {
                     cout << "t switch had a leading + ";
                     cout << "with a value of " << value;
                     }

(4)               status = parm.isSet(0,value);

                  if (status == ARG_NOT_SPECIFIED)
                     cout << "no file name given";
                  else
                     cout << "file name: " << value;
               }


               The above code demonstrates the basic use of the arg class.
                  (1) An instance of the object 'arg' is instantiated. The
                      first two parameters are simply those passed to main.
                      The last parameter (optional) is 1 if the switches are
                      case sensitive, else 0. 0 is the default.

                  (2) You will need string space to store any values associated
                      with a switch.

                  (3) This is the main member function used 'isSet'. This tests
                      to see if a specified flag was given and if so, what was
                      specified with it. The first argument is the char switch
                      name to look for. The second parameter is the user allocated
                      string space where any associated data is placed. The return
                      value will be one of four things:
                        ARG_NOT_SPECIFIED - this switch was not specified
                        ARG_CLEAR - this switch had a leading minus sign (-).
                        ARG_SET,  - this switch had a leading plus sign (+).
                        ARG_NO_SWITCH - this parameter is unlabeled

                  (4) This is how you obtain a value for a parameter that
                      does not use a leading + or -. This is known as an
                      unlabeled or unnamed parameter.

               In addition, there is one other member function that may be
               useful in debugging. It is called 'display'. This will display
               to stdout all of the switches that it found.

 Limitations: - Values for switches cannot contain spaces. That is, there must
                be no spaces between the switch label and its associated
                text. In addition, the associated text cannot contain spaces.

              - If a two parameters have the same label, the last parameter
                specified will be the one used in isSet. Likewise, if more
                than one non-labeled parameter is given, isSet can only access
                the last one specified.

              - There are no limitations to the number of command line
                arguments that can be read by 'arg'. You will only be limited
                by the maximum command line allowed by DOS.




 Created by:   Joe Kleinwaechter (j2k)
 Date:         15-Feb-1991

\****************************************************************************/

enum argState
   {   
   ARG_NOT_SPECIFIED=0,
   ARG_CLEAR,
   ARG_SET,
   ARG_NO_SWITCH
   };

class argString
   {
   public:
   argString *next;
   char letter;
   char *value;
   argState state;
   argString(char *);
   ~argString();
   };

   
class arg
   {
   private:
      argString *first;
      argString *locate(char);
      int caseSensitive;
   public:
      arg(int ac, char *av[],int c=0);
      ~arg();
      argState isSet(char, char []); //This determines whether a flag is set 
      void display(void);      //This outputs the current flag settings to stdout
   };


   
#endif

