#include "INCLUDE:Lattice/math.h"
#include "INCLUDE:Lattice/stdio.h"
#include "INCLUDE:exec/types.h"
#include "INCLUDE:graphics/gfx.h"
#include "INCLUDE:graphics/gfxmacros.h"
#include "INCLUDE:exec/exec.h"
#include "INCLUDE:exec/execbase.h"
#include "INCLUDE:graphics/view.h"
#include "INCLUDE:graphics/gfxbase.h"
#include "INCLUDE:exec/libraries.h"
#include "INCLUDE:intuition/intuition.h"
#include "INCLUDE:graphics/text.h"

#include "hp_constants.h"
#include "hp_data.include"

/*---------------------------------------*/
/*             //  hp  //                */
/*                                       */
/*     A public-domain scientific        */
/*      calculator for the Amiga         */
/*                                       */
/*            Version  1.0               */
/*             March 1987                */
/*            Steve Bonner               */
/*---------------------------------------*/

main()
{  int k;

GfxBase = (struct GfxBase *)OpenLibrary("graphics.library",0);
IntuitionBase = (struct IntuitionBase *)OpenLibrary("intuition.library",0);

if( (GfxBase == NULL) || (IntuitionBase == NULL)) exit();

xstr[33] = 0;
ystr[33] = 0;

print_on            = FALSE;
error_occurred      = FALSE;
entry_in_progress   = FALSE;
screen_refresh_only = FALSE;

for ( k = 0; k < 16; k++) {
    registers[k] = 0.0;
   iregisters[k] = 0;     }

for ( k =  0; k <= 12; k++) key_valid[k] = TRUE;
for ( k = 13; k <= 18; k++) key_valid[k] = FALSE;
for ( k = 19; k <= 64; k++) key_valid[k] = TRUE;

SetUpHpGraphics();

DrawDisplay();
screen_refresh_only = TRUE;

DrawKeys();
LabelKeys();

SetAngleMode( DEGREES );

base = HEX;         /*  Forces SetBase routine to highlight     */
SetBase( FLOAT );   /*  keys and zero out real and int stacks.  */

SetAPen( rp, GREY );
SetBPen( rp, SCREENCOLOR );
SetDrMd( rp, JAM2 );


DisplayFloatXY();

inkey = 0;

while ( 1 == 1) {

  NextClick:

  /*  Print command entered for last key click */
  PrintKey();

  KeyDown:

  /*  Wait for the next click:    */
  WaitPort( hp_window -> UserPort );

  if ( GadgetPoked() )        {
    CloseWindow( hp_window );
    CloseScreen( hp_screen );
    if ( print_on )      {
      fputs("\33#1", printer );    /* restore default setting */
      fclose( printer ); }
    exit();                   }

  if ( message -> Code != SELECTDOWN ) goto KeyDown;

  inkey = KeyCode();

  entry_completed = FALSE;

  if ( inkey == 31 ) StoreRegister();
  if ( inkey == 32 ) RecallRegister();

  if ( (inkey == 32) || (inkey == 32) ) goto NextClick;

  if ( key_valid[ inkey ] == FALSE ) {
    BeepHpDisplay();
    goto NextClick;                  }

  CheckModes();
  if ( mode_changed ) goto NextClick;


  if ( InkeyIsNumeric()  )              {

     if ( entry_in_progress )
        ContinueNumEntry();
     else
        CommenceNumEntry();             }


    else   /* Not numeric */            {

        if ( entry_in_progress )      {

          entry_completed = TRUE;

          /*  Convert instring to internal format   */
          /*  and push onto stack unless number is  */
          /*  being dropped:                        */
          if ( inkey != 60 ) PushX(); }

          /*  Perform a stack operation if requested  */
          CheckStack();

          error_occurred = FALSE;

          if ( base == FLOAT   )   ProcessFloat();
          if ( base == COMPLEX )   ProcessComplex();
          if ( base >= BINARY  )   ProcessInteger();

          entry_in_progress = FALSE;

          if ( error_occurred  )  {
             x  = 0.0;
             ix = 0;
             if ( base == COMPLEX ) y = 0.0;
             goto NextClick;       }

          if ( (inkey > 60) && (inkey < 64) ) {  TweakDisplay();
                                                 goto NextClick; }

          if ( inkey == 64 ) {  if (print_on) fprintf(printer, "\n");
                                goto NextClick;          }

          if ( base < 2 )
             DisplayFloatXY();
          else
             DisplayIntXY();
                                          }  /* Not numeric */
     

  }  /* WhileEnd */


}  /* main */

/*--------------------------------------------------------*/
/*    Bring in source code for subroutines:               */
/*--------------------------------------------------------*/

#include "hp_graphics1.include"
#include "hp_graphics2.include"

#include "hp_modes.include"
#include "hp_user_inputs.include"
#include "hp_conversions.include"
#include "hp_math.include"

/*--------------------------------------------------------*/
PrintKey()
{
 char *xp, *yp;
 if ((inkey == 0) || (inkey > 60)) return(0);

 if ( inkey == 55 )
   {
   if ( print_on == TRUE )       {
      print_on = FALSE;
      fputs("\33#1", printer );    /* restore default setting */
      fclose( printer );         }

   else                          {
      print_on = TRUE;
      printer  = fopen( "PRT:" , "w");
      if ( printer == NULL ) BeepHpDisplay();

      /*  Use condensed print (required for printing binary numbers) */
      fputs("\33[4w", printer);

      /*  Use printer color number 1  */
      fputs("\33[31m", printer);   }
   }

 if ( print_on == FALSE ) return(0);

 if ( entry_in_progress == FALSE )   {

   /*  If a new x-value has just been Pushed, it must be printed */
   if ( entry_completed )        {
     iptr = &instring[0];
     instring[ next_digit ] = 0; }
   else
     iptr = &nullentry[0];

   if ( base < BINARY ) {  xp = xptr;
                           yp = yptr;     }
   else                 {  xp = &xstr[0];
                           yp = &ystr[0]; }


   /*  If command is STO or RCL, set pointer to identify register */
   if ( (inkey == 31) || (inkey == 32))
     regptr = opcode[ regcode ];
   else
     regptr = &no_register[0];

   fprintf( printer, "%-32s %5s %5s %-32s %-32s\n",
         iptr, opcode[inkey], regptr, yp, xp );
                                    }
}



