home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / misc / volume1 / 8710 / 3 < prev    next >
Encoding:
Text File  |  1990-07-13  |  47.3 KB  |  1,740 lines

  1. Path: uunet!munnari!otc!metro!basser!richb
  2. From: richb@sunk.oz.AU (Rich Burridge)
  3. Newsgroups: comp.sources.misc
  4. Subject: Calctool v1.4.
  5. Message-ID: <1040@basser.oz>
  6. Date: 7 Oct 87 01:28:14 GMT
  7. Sender: john@basser.oz
  8. Reply-To: richb@sunk.oz.AU (Rich Burridge0
  9. Lines: 1728
  10. Approved: john@basser.cs.su.oz.AU
  11.  
  12. #! /bin/sh
  13. # this is a shell archive, meaning:
  14. # 1. Remove everything above the #! /bin/sh line
  15. # 2. Save the resulting text in a file.
  16. # 3. Execute the file with /bin/sh to create the files:
  17. #    README
  18. #    Makefile
  19. #    calctool.c
  20. #    functions.c
  21. #    calctool.h
  22. #    patchlevel.h
  23. #    button.icon
  24. #    calctool.icon
  25. #    help.cursor
  26. #    calctool.help
  27. # This archive created: Mon Oct  5 13:20:46 EST 1987
  28. #
  29. #
  30. export PATH; PATH=/bin:$PATH
  31. #
  32. if [ -f README ]
  33. then
  34. echo shar: will not over-write existing file README
  35. else
  36. echo shar: extracting 'README',     2017 characters
  37. cat > README <<'Funky_Stuff'
  38.  
  39. calctool  -  README  -  2nd September 1987.
  40.  
  41. This is V1.4 of a simple desktop calculator for the Sun workstation.
  42. Some of it's features include:
  43.  
  44.  (1) You can GET and PUT the calculator display.
  45.  (2) Every calculator button has an equivalent key press.
  46.  (3) Built in help, press HLP followed by another selection.
  47.  (4) Normal arithmetic + - x / with constants.
  48.  (6) Logical operations AND OR XOR XNOR and NOT.
  49.  (7) Results can be displayed (and calculated) in binary, octal,
  50.      decimal and hexidecimal.
  51.  (8) The result can be shifted multiple places to the left and right.
  52.  (9) Fractional precision can be 0 to 9 places.
  53. (10) There are ten memory registers for storing and retrieving numbers.
  54. (11) A backspace key to remove last character of the display. Note
  55.      that this loses internal numeric accuracy as the number is
  56.      recalculated from the display value.
  57.  
  58. Thanks to Ed Falk at Sun Microsystems (Mountain View) for some of the
  59. basic algorithms used.
  60.  
  61. Thanks to Paul Czarnecki for the fix to the binary display problem.
  62.  
  63. Thanks to Rich Baughman at the Consumer Financial Institute in Newton
  64. MA, for the following features:
  65.  
  66. (1) An alternate display for the button values (using the right mouse button
  67.     as the display toggle) that shows the keyboard equivalent input character.
  68.  
  69. (2) A memory register display screen that shows all the registers in the
  70.     calculator (using the middle mouse button as the display toggle).
  71.     This is helpful when trying to remember what values are stored in those
  72.     registers.
  73.  
  74. You can now change where the program reads the helpfile information from,
  75. via the -h command line option. 
  76.  
  77. Suggestions for furthur improvement would be most welcome plus bugs,
  78. comments and flames to me.
  79.  
  80. Regards Rich.
  81.  
  82. Rich Burridge,            JANET richb%sunk.oz@uk.ac.ucl.cs
  83. ACSnet  richb@sunk.oz     UUCP {seismo,hplabs,ukc}!munnari!sunk.oz!richb
  84. PHONE: +61 3 811 9927     ARPAnet richb%sunk.oz@seismo.css.gov
  85. MAIL: Sun Microsystems, 123 Camberwell Rd, Hawthorn, VICTORIA 3122, AUST
  86. Funky_Stuff
  87. len=`wc -c < README`
  88. if [ $len !=     2017 ] ; then
  89. echo error: README was $len bytes long, should have been     2017
  90. fi
  91. fi # end of overwriting check
  92. if [ -f Makefile ]
  93. then
  94. echo shar: will not over-write existing file Makefile
  95. else
  96. echo shar: extracting 'Makefile',     1191 characters
  97. cat > Makefile <<'Funky_Stuff'
  98. #
  99. #  Makefile for calctool, a simple calculator.
  100. #
  101. #  Copyright (c) Rich Burridge - September 1987.
  102. #                Sun Microsystems, Australia - All rights reserved.
  103. #
  104. #  Includes code and ideas from:
  105. #                Rich Baughman, Consumer Financial Institute, Newton, MA
  106. #
  107. #  Version 1.4.
  108. #
  109. #  No responsibility is taken for any errors inherent either in the comments
  110. #  or the code of this program, but if reported to me then an attempt will
  111. #  be made to fix them.
  112. #
  113.  
  114. BINARIES      = calctool
  115. BINDIR        = .
  116. CFLAGS        = -g
  117. LDFLAGS       = -g
  118. OBJS          = calctool.o functions.o
  119. SRCS          = calctool.c functions.c
  120. HDRS          = calctool.h
  121. IMAGES        = button.icon calctool.icon help.cursor
  122. LIBS          = -lm -lsuntool -lsunwindow -lpixrect
  123.  
  124. all:            $(BINARIES)
  125.  
  126. release:        $(BINARIES)
  127.         strip $(BINARIES)
  128.  
  129. backup:
  130.         cp calctool.h calctool.h~
  131.         cp calctool.c calctool.c~
  132.         cp calctool.help calctool.help~
  133.         cp functions.c functions.c~
  134.  
  135. clean:
  136.         rm -f *.o core
  137.  
  138. lint:
  139.         lint $(SPECIAL) $(SRCS) $(LIBS)
  140.  
  141. calctool:       $(OBJS)
  142.         cc $(LDFLAGS) -o calctool $(OBJS) $(LIBS)
  143.  
  144. calctool.o:     calctool.c $(HDRS) $(IMAGES)
  145. functions.o:    functions.c $(HDRS)
  146. Funky_Stuff
  147. len=`wc -c < Makefile`
  148. if [ $len !=     1191 ] ; then
  149. echo error: Makefile was $len bytes long, should have been     1191
  150. fi
  151. fi # end of overwriting check
  152. if [ -f calctool.c ]
  153. then
  154. echo shar: will not over-write existing file calctool.c
  155. else
  156. echo shar: extracting 'calctool.c',    18907 characters
  157. cat > calctool.c <<'Funky_Stuff'
  158.  
  159. /*  calctool.c
  160.  *
  161.  *  This program looks and acts like a simple calculator.
  162.  *
  163.  *  Copyright (c) Rich Burridge - September 1987.
  164.  *                Sun Microsystems, Australia - All rights reserved.
  165.  *
  166.  *  Includes ideas and code from:
  167.  *                Rich Baughman, Consumer Financial Institute, Newton, MA
  168.  *
  169.  *  Version 1.4.
  170.  *
  171.  *  No responsibility is taken for any errors or inaccuracies inherent
  172.  *  either to the comments or the code of this program, but if
  173.  *  reported to me then an attempt will be made to fix them.
  174.  */
  175.  
  176. #include "patchlevel.h"
  177. #include "calctool.h"
  178.  
  179. void canvas_proc() ;
  180. Panel_setting panel_proc() ;
  181.  
  182. Canvas canvas, rcanvas ;
  183. Cursor main_cursor ;
  184. Event event ;
  185. Frame frame, rframe ;
  186. Icon calctool_icon ;
  187. Panel panel ;
  188. Panel_item base_item, display_item ;
  189. Pixfont *sfont, *nfont ;
  190. Pixwin *cpw, *rcpw ;
  191.  
  192. short help_cursor_array[16] = {
  193. #include "help.cursor"
  194. } ;
  195. mpr_static(help_cursor_pr,16,16,1,help_cursor_array) ;
  196. struct cursor help_cursor =
  197.          { 0, 0, PIX_SRC | PIX_DST, &help_cursor_pr } ;
  198.  
  199. short button_image[] = {
  200. #include "button.icon"
  201. } ;
  202. mpr_static(button_pr,64,64,1,button_image) ;
  203.  
  204. short icon_image[] = {
  205. #include "calctool.icon"
  206. } ;
  207. mpr_static(icon_pixrect,64,64,1,icon_image) ;
  208.  
  209. double powers[11][4] = {
  210.          {    1.0,          1.0,           1.0,             1.0 },
  211.          {    2.0,          8.0,          10.0,            16.0 },
  212.          {    4.0,         64.0,         100.0,           256.0 },
  213.          {    8.0,        512.0,        1000.0,          4096.0 },
  214.          {   16.0,       4096.0,       10000.0,         65536.0 },
  215.          {   32.0,      32768.0,      100000.0,       1048576.0 },
  216.          {   64.0,     262144.0,     1000000.0,      16777216.0 },
  217.          {  128.0,    2097152.0,    10000000.0,     268435456.0 },
  218.          {  256.0,   16777216.0,   100000000.0,    4294967296.0 },
  219.          {  512.0,  134217728.0,  1000000000.0,   68719476736.0 },
  220.          { 1024.0, 1073741824.0, 10000000000.0, 1099511627776.0 }
  221. } ;
  222.  
  223. /* Length of display in characters for each base. */
  224. int disp_length[4] = {32, 15, 12, 12} ;
  225.  
  226. double disp_val ;             /* Value of the current display. */
  227. double last_input ;           /* Previous number input by user. */
  228. double mem_vals[MAXREGS] ;    /* Memory register values. */
  229. double result ;               /* Current calculator total value. */
  230.  
  231. FILE *hfd ;             /* File descriptor for help information. */
  232.  
  233. int accuracy ;          /* Number of digits precision (Max 9). */
  234. int base ;              /* Current base: BIN, OCT, DEC or HEX. */
  235. int column ;            /* Column number of key pressed. */
  236. int error ;             /* Indicates some kind of display error. */
  237. int n ;                 /* Index into buttons array structure. */
  238. int new_input ;         /* New number input since last op. */
  239. int nohelp ;            /* Indicates if a help file was found. */
  240. int pointed ;           /* Whether a decimal point has been given. */
  241. int row ;               /* Row number of key pressed. */
  242. int rstate ;            /* Indicates if memory register frame is displayed. */
  243. int toclear ;           /* Indicates if display should be cleared. */
  244. int tstate ;            /* Indicates current button set being displayed. */
  245.  
  246. /* Routines obeyed by mouse button or character presses. */
  247. do_accuracy(), do_base(), do_calculation(), do_clear() ;
  248. do_close(), do_delete(), do_help(), do_memory(), do_not() ;
  249. do_number(), do_point(), do_quit(), do_shift(), do_sqrt() ;
  250.  
  251. char c ;                /* Current character typed by the user. */
  252. char cur_op ;           /* Current arithmetic operation. */
  253. char cur_value ;        /* Current button or character pressed. */
  254. char old_cal_value ;    /* Previous calculation operator. */
  255.  
  256. struct button buttons[TOTAL_ITEMS] = {         /* Calculator button values. */
  257.          { "<<",  do_shift,       '<' },       /* Row 1. */
  258.          { "BIN", do_base,        'B' },
  259.          { "OCT", do_base,        'O' },
  260.          { "DEC", do_base,        'D' },
  261.          { "HEX", do_base,        'H' },
  262.          { ">>",  do_shift,       '>' },
  263.  
  264.          { "STO", do_memory,      's' },       /* Row 2. */
  265.          { "RCL", do_memory,      'r' },
  266.          { " D ", do_number,      'd' },
  267.          { " E ", do_number,      'e' },
  268.          { " F ", do_number,      'f' },
  269.          { "CLR", do_clear,       '\177' },
  270.  
  271.          { "NOT", do_not,         '~' },       /* Row 3. */
  272.          { "SQR", do_sqrt,        'S' },
  273.          { " A ", do_number,      'a' },
  274.          { " B ", do_number,      'b' },
  275.          { " C ", do_number,      'c' },
  276.          { "BSP", do_delete,      '\010' },
  277.  
  278.          { "AND", do_calculation, '&' },       /* Row 4. */
  279.          { "OR",  do_calculation, '|' },
  280.          { " 7 ", do_number,      '7' },
  281.          { " 8 ", do_number,      '8' },
  282.          { " 9 ", do_number,      '9' },
  283.          { " X ", do_calculation, 'x' },
  284.  
  285.          { "XOR", do_calculation, '^' },       /* Row 5. */
  286.          { "XNR", do_calculation, 'n' },
  287.          { " 4 ", do_number,      '4' },
  288.          { " 5 ", do_number,      '5' },
  289.          { " 6 ", do_number,      '6' },
  290.          { " / ", do_calculation, '/' },
  291.  
  292.          { "ACC", do_accuracy,    'A' },       /* Row 6. */
  293.          { "HLP", do_help,        '?' },
  294.          { " 1 ", do_number,      '1' },
  295.          { " 2 ", do_number,      '2' },
  296.          { " 3 ", do_number,      '3' },
  297.          { " - ", do_calculation, '-' },
  298.  
  299.          { "OFF", do_close,       '\033' },    /* Row 7. */
  300.          { "END", do_quit,        'q' },
  301.          { " 0 ", do_number,      '0' },
  302.          { " . ", do_point,       '.' },
  303.          { " = ", do_calculation, '=' },
  304.          { " + ", do_calculation, '+' },
  305.  
  306.          { "   ", do_calculation, 'X' },        /* Extra useful definitions. */
  307.          { "   ", do_calculation, '*' },
  308.          { "   ", do_calculation, '\015' },
  309.          { "   ", do_quit,        'Q' },
  310.          { "   ", do_calculation, 'N' },
  311. } ;
  312.  
  313. char display[MAXLINE] ;             /* Current calculator display. */
  314. char helpname[MAXLINE] ;            /* Filename for help file. */
  315. char progname[MAXLINE] ;            /* Name of this program. */
  316.  
  317.  
  318. main(argc,argv)
  319. int argc ;
  320. char *argv[] ;
  321.  
  322. {
  323.   STRCPY(progname,argv[0]) ;        /* Save this programs name. */
  324.   get_options(argc,argv) ;          /* Get command line arguments. */
  325.   nohelp = 0 ;
  326.   if ((hfd = fopen(helpname,"r")) == NULL)
  327.     {
  328.       FPRINTF(stderr,"Help file %s not found\r\n",HELPNAME) ;
  329.       nohelp = 1 ;
  330.     }
  331.  
  332.   sfont = pf_open(SMALLFONT) ;      /* Open small point font. */
  333.   nfont = pf_open(NORMALFONT) ;     /* Open normal sized font. */
  334.   calctool_icon = icon_create(ICON_WIDTH,42,
  335.                               ICON_IMAGE,&icon_pixrect,
  336.                               0) ;
  337.  
  338.   frame = window_create((Window) 0, FRAME,
  339.                         FRAME_ICON, calctool_icon,
  340.                         FRAME_SHOW_LABEL, FALSE,
  341.                         FRAME_SUBWINDOWS_ADJUSTABLE, FALSE,
  342.                         FRAME_NO_CONFIRM, TRUE,
  343.                         WIN_TOP_MARGIN, DISPLAY,
  344.                         WIN_ROW_HEIGHT, BUTTON_HEIGHT,
  345.                         WIN_COLUMN_WIDTH, BUTTON_WIDTH,
  346.                         WIN_ROWS, BUTTON_ROWS,
  347.                         WIN_COLUMNS, BUTTON_COLS,
  348.                         FRAME_ARGS, argc,argv,
  349.                         0) ;
  350.   rframe = window_create(frame, FRAME,
  351.                          FRAME_SHOW_LABEL, FALSE,
  352.                          FRAME_NO_CONFIRM, TRUE,
  353.                          WIN_WIDTH,TOTAL_WIDTH+60,
  354.                          WIN_HEIGHT,TOTAL_HEIGHT+10,
  355.                          WIN_FONT,nfont,
  356.                          WIN_Y,(int) window_get(frame, WIN_Y) + DISPLAY + 5,
  357.                          WIN_X,(int) window_get(frame, WIN_X) + TOTAL_WIDTH + 15,
  358.                          0) ;
  359.  
  360.   panel = window_create(frame, PANEL,
  361.                         WIN_CONSUME_KBD_EVENTS, WIN_ASCII_EVENTS, 0,
  362.                         WIN_HEIGHT, DISPLAY,
  363.                         0) ;
  364.   rcanvas = window_create(rframe,CANVAS,0) ;
  365.  
  366.   canvas = window_create(frame,CANVAS,
  367.                          WIN_BELOW,panel,
  368.                          WIN_WIDTH,TOTAL_WIDTH,
  369.                          WIN_HEIGHT,TOTAL_HEIGHT,
  370.                          WIN_FONT,nfont,
  371.                          WIN_EVENT_PROC,canvas_proc,
  372.                          0) ;
  373.   WINDOW_SET(canvas,WIN_CONSUME_KBD_EVENT,WIN_ASCII_EVENTS,0) ;
  374.  
  375.   display_item = panel_create_item(panel,PANEL_TEXT,
  376.                                    PANEL_VALUE_Y,DISPLAY-25,
  377.                                    PANEL_NOTIFY_LEVEL, PANEL_ALL,
  378.                                    PANEL_ACCEPT_KEYSTROKE, 1,
  379.                                    PANEL_NOTIFY_PROC, panel_proc,
  380.                                    PANEL_VALUE_FONT,nfont,
  381.                                    0) ;
  382.   base_item = panel_create_item(panel,PANEL_MESSAGE,
  383.                                 PANEL_LABEL_X,10,
  384.                                 PANEL_LABEL_Y,DISPLAY-10,
  385.                                 PANEL_LABEL_FONT,sfont,
  386.                                 PANEL_LABEL_STRING,"",
  387.                                 0) ;
  388.   cpw = canvas_pixwin(canvas) ;
  389.   rcpw = canvas_pixwin(rcanvas) ;
  390.   main_cursor = window_get(canvas,WIN_CURSOR) ;
  391.  
  392.   rstate = 0 ;                /* No memory register frame display initially. */
  393.   tstate = 0 ;                /* Button values displayed first. */
  394.   base = DEC ;                /* Initial base. */
  395.   accuracy = 2 ;              /* Initial accuracy. */
  396.   do_clear() ;                /* Initialise and clear display. */
  397.  
  398.   make_registers() ;          /* Calculate memory register frame values. */
  399.   make_canvas(0) ;            /* Draw the calculators buttons. */
  400.   window_fit(frame) ;
  401.   window_main_loop(frame) ;
  402.   exit(0) ;
  403. }
  404.  
  405.  
  406. /*ARGSUSED*/
  407. Panel_setting
  408. panel_proc(item,event)
  409. Panel_item item ;
  410. Event *event ;
  411.  
  412. {
  413.   int chr ;
  414.  
  415.   chr = event_id(event) ;
  416.   for (n = 0; n < TOTAL_ITEMS; n++)
  417.     {
  418.       if (chr == buttons[n].value)
  419.         {
  420.           PANEL_SET(item,PANEL_NOTIFY_LEVEL,PANEL_NONE,0) ;
  421.           process_item(n) ;
  422.           PANEL_SET(item,PANEL_NOTIFY_LEVEL,PANEL_ALL,0) ;
  423.           return ;
  424.         }
  425.     }
  426. }
  427.  
  428.  
  429. /*ARGSUSED*/
  430. static void
  431. canvas_proc(win,event,arg)
  432. Canvas  win ;
  433. Event *event ;
  434. caddr_t arg ;
  435.  
  436. {
  437.   int column,row ;
  438.  
  439.   if (event_is_button(event) && event_is_up(event))
  440.     {
  441.       switch (event_id(event))
  442.         {
  443.           case MS_LEFT   : column = event_x(event) / (BUTTON_WIDTH + BUTTON_GAP) ;
  444.                            row = event_y(event) / (BUTTON_HEIGHT + BUTTON_GAP) ;
  445.                            n = row*BUTTON_COLS+column ;
  446.                            break ;
  447.           case MS_MIDDLE : toggle_reg_canvas() ;
  448.                            return ;
  449.           case MS_RIGHT  : make_canvas(1) ;
  450.                            return ;
  451.         }
  452.     }
  453.   else if (event_is_ascii(event))
  454.     {
  455.       for (n = 0; n < TOTAL_ITEMS; n++)
  456.         if (event_id(event) == buttons[n].value) break ;
  457.       if (n == TOTAL_ITEMS) return ;
  458.     }
  459.   else return ;
  460.  
  461.   process_item(n) ;
  462. }
  463.  
  464.     
  465. process_item(n)
  466. int n ;
  467.  
  468. {
  469.   cur_value = buttons[n].value ;
  470.  
  471.   if (cur_value == 'X') cur_value = 'x' ;       /* Reassign "extra" values. */
  472.   if (cur_value == '*') cur_value = 'x' ;
  473.   if (cur_value == '\015') cur_value = '=' ;
  474.   if (cur_value == 'Q') cur_value = 'q' ;
  475.   if (cur_value == 'N') cur_value = 'n' ;
  476.  
  477.   if (error && cur_value != '\177') return ;    /* If error, must clear first. */
  478.  
  479.   (*buttons[n].func)() ;
  480. }
  481.  
  482.  
  483. char_val(chr)
  484. char chr ;
  485.  
  486. {
  487.        if (chr >= '0' && chr <= '9') return(chr - '0') ;
  488.   else if (chr >= 'a' && chr <= 'f') return(chr - 'a' + 10) ;
  489.   else return(-1) ;
  490. }
  491.  
  492.  
  493. clear_display()
  494.  
  495. {
  496.   int i ;
  497.  
  498.   pointed = 0 ;
  499.   toclear = 1 ;
  500.   STRCPY(display,"0.") ;
  501.   for (i = 0; i < accuracy; i++)
  502.     STRNCAT(display,"0",1) ;
  503.   display_result(display) ;
  504.   disp_val = 0.0 ;
  505. }
  506.  
  507.  
  508. double
  509. convert_display()    /* Convert input string into a double. */
  510.  
  511. {
  512.   static int basevals[4] = {2, 8, 10, 16} ;
  513.   int i,inum ;
  514.   double val ;
  515.   char *optr ;
  516.  
  517.   val = 0.0 ;
  518.   optr = display ;
  519.   while ((inum = char_val(*optr)) >= 0)
  520.     {
  521.       val = val * basevals[base] + inum ;
  522.       *optr++ ;
  523.     }
  524.       
  525.   if (*optr == '.')
  526.     for (i = 1; (inum = char_val(*++optr)) >= 0; i++)
  527.       val += inum / powers[i][base] ;
  528.   return(val) ;
  529. }
  530.  
  531.  
  532. display_base(base)
  533. int base ;
  534.  
  535. {
  536.   char base_str[MAXLINE] ;
  537.  
  538.   switch (base)
  539.     {
  540.       case BIN : STRCPY(base_str,"BIN") ;
  541.                  break ;
  542.       case OCT : STRCPY(base_str,"OCT") ;
  543.                  break ;
  544.       case DEC : STRCPY(base_str,"") ;
  545.                  break ;
  546.       case HEX : STRCPY(base_str,"HEX") ;
  547.     }
  548.   PANEL_SET(base_item,PANEL_LABEL_STRING,base_str,0) ;
  549. }
  550.  
  551.  
  552. display_result(display)       /* Output result to calculator display. */
  553. char display[MAXLINE] ;
  554.  
  555. {
  556.   PANEL_SET(display_item,PANEL_VALUE_X,20+(MAX_DIGITS - strlen(display))*7,
  557.                          PANEL_VALUE,display,
  558.                          0) ;
  559. }
  560.  
  561.  
  562. get_next_value()              /* Get next key or mouse button press. */
  563.  
  564. {
  565.   int column,found,n,row ;
  566.    
  567.   found = 0 ;
  568.   while (!found)
  569.     {
  570.       WINDOW_READ_EVENT(canvas,&event) ;
  571.       if (event_is_button(&event) && event_is_up(&event))
  572.         {
  573.           column = event_x(&event) / (BUTTON_WIDTH + BUTTON_GAP) ;
  574.           row = event_y(&event) / (BUTTON_HEIGHT + BUTTON_GAP) ;
  575.           n = row*BUTTON_COLS+column ;
  576.           if (n < TOTAL_ITEMS) found = 1 ;
  577.         }
  578.       else if (event_is_ascii(&event))
  579.         {
  580.           c = event_id(&event) ;
  581.           for (n = 0; n < TOTAL_ITEMS; n++)
  582.             if (c == buttons[n].value)
  583.               {
  584.                 found = 1 ;
  585.                 break ;
  586.               }
  587.         }
  588.     }
  589.   return(n) ;
  590. }
  591.  
  592.  
  593. get_options(argc,argv)        /* Extract command line options. */
  594. int argc ;
  595. char *argv[] ;
  596.  
  597. {
  598.   char *arg ;
  599.   char *p ;      /* Pointer to string following argument flag. */
  600.  
  601.   STRCPY(helpname,HELPNAME) ;    /* Default help filename. */
  602.   while (argc > 1 && (arg = argv[1])[0] == '-')
  603.     {
  604.       p = arg + 2 ;
  605.       switch (arg[1])
  606.         {
  607.           case 'h' : STRCPY(helpname,p) ;      /* Get new help filename. */
  608.                      break ;
  609.           case 'v' : FPRINTF(stderr,"%s version 1.4.%1d\n",progname,PATCHLEVEL) ;
  610.                      break ;
  611.           case '?' : FPRINTF(stderr,"USAGE %s [-hhelpfile] [-v] [-?]\n",progname) ;
  612.                      exit(1) ;
  613.         }
  614.       argc-- ;
  615.       argv++ ;
  616.     }
  617. }
  618.  
  619.  
  620. initialise()
  621.  
  622. {
  623.   error = 0 ;                 /* Currently no display error. */
  624.   cur_op = '?' ;              /* No arithmetic operator defined yet. */
  625.   old_cal_value = '?' ;
  626.   result = 0.0 ;              /* No previous result yet. */
  627.   last_input = 0.0 ;
  628. }
  629.  
  630.  
  631. make_canvas(toggle)           /* Draw the calculators buttons. */
  632. int toggle ;                  /* Should we toggle the display of buttons. */
  633. {
  634.   int n,x ;
  635.   char pstr[10] ;
  636.  
  637.   if (toggle) tstate = !tstate ;
  638.  
  639. /*  Each call alternates button display, between display string, and
  640.  *  single-char input character.
  641.  */
  642.  
  643.   pw_writebackground(cpw,0,0,TOTAL_WIDTH,TOTAL_HEIGHT,PIX_CLR) ;
  644.   for (row = 0; row < BUTTON_ROWS; row++)
  645.     for (column = 0; column < BUTTON_COLS; column++)
  646.       {
  647.         n = row * BUTTON_COLS + column ;
  648.         if (tstate)
  649.           {
  650.             switch (buttons[n].value)
  651.               {
  652.                 case '\010' : STRCPY(pstr,"BSP") ;
  653.                               break ;
  654.                 case '\033' : STRCPY(pstr,"ESC") ;
  655.                               break ;
  656.                 case '\177' : STRCPY(pstr,"DEL") ;
  657.                               break ;
  658.                 default     : SPRINTF(pstr," %c ",buttons[n].value) ;
  659.               }
  660.           }
  661.         else STRCPY(pstr,buttons[n].str) ;
  662.  
  663.         pw_write(cpw,column*BUTTON_WIDTH+BUTTON_BORDER+(column*BUTTON_GAP),
  664.                      row*BUTTON_HEIGHT+BUTTON_BORDER+(row*BUTTON_GAP),
  665.                      BUTTON_WIDTH,BUTTON_HEIGHT,PIX_SRC,&button_pr,0,0) ;
  666.         x = (strlen(pstr) == 3) ? 8 : 11 ;
  667.         pw_text(cpw,column*BUTTON_WIDTH+BUTTON_BORDER+(column*BUTTON_GAP)+x,
  668.                           row*BUTTON_HEIGHT+BUTTON_BORDER+(row*BUTTON_GAP)+14,
  669.                           PIX_SRC | PIX_DST,nfont,pstr) ;
  670.       }
  671. }
  672.  
  673.  
  674. make_display(display)    /* Output calculators display - right justified. */
  675. char display[MAXLINE] ;
  676.  
  677. {
  678.   PANEL_SET(display_item,PANEL_VALUE_X,20+(MAX_DIGITS - strlen(display))*7,
  679.                          PANEL_VALUE,display,
  680.                          0) ;
  681. }
  682.  
  683.  
  684. char *
  685. make_number(number)        /* Convert display value to current base. */
  686. double number ;            /* Value to convert. */
  687.  
  688. {
  689.   char *optr,display[MAXLINE] ;
  690.   double val ;
  691.   int cmax ;               /* Maximum number of characters to display. */
  692.   int ndig ;               /* Total number of digits to generate. */
  693.   int ddig ;               /* Number of digits to left of . */
  694.   int dval ;
  695.   static char digits[] = "0123456789abcdef" ;
  696.  
  697.   if (isinf(number) || isnan(number))
  698.     {
  699.       STRCPY(display,"Error") ;
  700.       error = 1 ;
  701.       return(display) ;
  702.     }
  703.  
  704.   cmax = disp_length[base] ;
  705.   optr = display ;
  706.   val = fabs(number) ;
  707.   if (number < 0.0) *optr++ = '-' ;
  708.   val += .5 / powers[accuracy][base] ;
  709.  
  710.   if (val < 1.0)
  711.     {
  712.       ddig = 0 ;
  713.       *optr++ = '0' ;
  714.       cmax-- ;
  715.     }
  716.   else
  717.     {
  718.       for (ddig = 0; val >= 1.0; ddig++)
  719.         val /= powers[1][base] ;
  720.     }
  721.  
  722.   if ((ndig = ddig + accuracy) > cmax)
  723.     {
  724.       if (ddig > cmax)
  725.         {
  726.           STRCPY(display,"Overflow") ;
  727.           error = 1 ;
  728.           return(display) ;
  729.         }
  730.       else
  731.         {
  732.           STRCPY(display,"Reducing precision") ;
  733.           display_result(display) ;
  734.           sleep(1) ;
  735.           bzero(display,MAXLINE) ;
  736.           accuracy = cmax - ddig ;
  737.           if (accuracy < 0) accuracy = 0 ;
  738.           ndig = ddig + accuracy ;
  739.         }
  740.     }
  741.  
  742.   while (ndig-- > 0)
  743.     {
  744.       if (ddig-- == 0) *optr++ = '.' ;
  745.       val *= powers[1][base] ;
  746.       dval = val ;
  747.       *optr++ = digits[dval] ;
  748.       val -= (int) val ;
  749.     }
  750.  *optr++ = '\0' ;
  751.   toclear = 1 ;
  752.   pointed = 0 ;
  753.   return(display) ;
  754. }
  755.  
  756.  
  757. make_registers()           /* Calculate memory register frame values. */
  758.  
  759. {
  760.   char line[MAXLINE] ;     /* Current memory register line. */
  761.   int n ;
  762.   int height,width ;       /* Dimensions of this frame. */
  763.  
  764.   height = (int) window_get(rframe,WIN_HEIGHT) ;
  765.   width = (int) window_get(rframe,WIN_WIDTH) ;
  766.   pw_writebackground(rcpw,0,0,width,height,PIX_CLR) ;
  767.   pw_text(rcpw,15,20,PIX_SRC,nfont,"MEMORY REGISTERS") ;
  768.   for (n = 0; n < MAXREGS; n++)
  769.     {
  770.       SPRINTF(line,"%1d   ",n) ;
  771.       STRCAT(line,make_number(mem_vals[n])) ;
  772.       pw_text(rcpw,15,40+15*n,PIX_SRC,nfont,line) ;
  773.     }
  774. }
  775.  
  776.  
  777. make_text(x,y,line)        /* Output a line of text. */
  778. int x,y ;
  779. char line[MAXLINE] ;
  780.  
  781. {
  782.   pw_text(cpw,x,y,PIX_SRC,nfont,line) ;
  783. }
  784.  
  785.  
  786. toggle_reg_canvas()
  787.  
  788. {
  789.   rstate = !rstate ;
  790.   if (rstate) WINDOW_SET(rframe, WIN_SHOW, TRUE, 0) ;
  791.   else WINDOW_SET(rframe, WIN_SHOW, FALSE, 0) ;
  792. }
  793. Funky_Stuff
  794. len=`wc -c < calctool.c`
  795. if [ $len !=    18907 ] ; then
  796. echo error: calctool.c was $len bytes long, should have been    18907
  797. fi
  798. fi # end of overwriting check
  799. if [ -f functions.c ]
  800. then
  801. echo shar: will not over-write existing file functions.c
  802. else
  803. echo shar: extracting 'functions.c',     9184 characters
  804. cat > functions.c <<'Funky_Stuff'
  805.  
  806. /*  functions.c
  807.  *
  808.  *  This file contains the seperate functions used whenever a calculator
  809.  *  button is pressed.
  810.  *
  811.  *  Copyright (c) Rich Burridge - September 1987.
  812.  *                Sun Microsystems, Australia - All rights reserved.
  813.  *
  814.  *  Includes ideas and code from:
  815.  *                Rich Baughman, Consumer Financial Institute, Newton, MA
  816.  *
  817.  *  Version 1.4.
  818.  *
  819.  *  No responsibility is taken for any errors or inaccuracies inherent
  820.  *  either to the comments or the code of this program, but if
  821.  *  reported to me then an attempt will be made to fix them.
  822.  */
  823.  
  824. #include "calctool.h"
  825.  
  826. double setbool() ;
  827.  
  828. extern char *make_number() ;
  829. extern double convert_display() ;
  830.  
  831. extern Canvas canvas ;
  832. extern Cursor main_cursor ;
  833. extern Event event ;
  834. extern Frame frame, rframe ;
  835. extern Panel_item base_item ;
  836. extern Pixwin *cpw ;
  837. extern struct cursor help_cursor ;
  838.  
  839. extern FILE *hfd ;                /* File descriptor for help information. */
  840. extern struct button buttons[] ;  /* Calculator button values. */
  841.  
  842. /* Length of display in characters for each base. */
  843. extern int disp_length[] ;
  844.  
  845. extern double disp_val ;          /* Value of the current display. */
  846. extern double last_input ;        /* Previous number input by user. */
  847. extern double mem_vals[] ;        /* Memory register values. */
  848. extern double result ;            /* Current calculator total value. */
  849.  
  850. extern int accuracy ;             /* Number of digits precision (Max 9). */
  851. extern int base ;                 /* Current base: BIN, OCT, DEC or HEX. */
  852. extern int new_input ;            /* New number input since last op. */
  853. extern int nohelp ;               /* Indicates if a help file was found. */
  854. extern int pointed ;              /* Whether a decimal point has been given. */
  855. extern int toclear ;              /* Indicates if display should be cleared. */
  856.  
  857. extern char cur_op ;              /* Current arithmetic operation. */
  858. extern char cur_value ;           /* Current button or character pressed. */
  859. extern char old_cal_value ;       /* Previous calculation operator. */
  860. extern char display[MAXLINE] ;    /* Current calculator display. */
  861.  
  862.  
  863. do_accuracy()       /* Get value for number of digits accuracy. */
  864.  
  865. {
  866.   int n,valid ;
  867.  
  868.   valid = 0 ;
  869.   while (!valid)
  870.     {
  871.       n = get_next_value() ;
  872.       if (buttons[n].value >= '0' && buttons[n].value <= '9')
  873.         {
  874.           accuracy = char_val(buttons[n].value) ;
  875.           valid = 1 ;
  876.         }
  877.     }
  878.   STRCPY(display,make_number(disp_val)) ;
  879.   display_result(display) ;
  880.   make_registers() ;
  881. }
  882.  
  883.  
  884. do_base()    /* Change the current base setting. */
  885.  
  886. {
  887.   switch (cur_value)
  888.     {
  889.       case 'B' : base = BIN ;
  890.                  break ;
  891.       case 'O' : base = OCT ;
  892.                  break ;
  893.       case 'D' : base = DEC ;
  894.                  break ;
  895.       case 'H' : base = HEX ;
  896.     }
  897.   display_base(base) ;
  898.   STRCPY(display,make_number(disp_val)) ;   /* Convert display value to current base. */
  899.   display_result(display) ;
  900.   make_registers() ;
  901. }
  902.  
  903.  
  904. do_calculation()      /* Perform arithmetic calculation and display result. */
  905.  
  906. {
  907.   int isboolean ;
  908.   BOOLEAN temp ;
  909.  
  910.   if (cur_value == '=' && old_cal_value == '=')
  911.     if (new_input) result = last_input ;
  912.     else disp_val = last_input ;
  913.  
  914.   if (cur_value != '=' && old_cal_value == '=') cur_op = '?' ;
  915.   isboolean = 0 ;
  916.  
  917.   switch (cur_op)
  918.     {
  919.       case '?'    : result = disp_val ;          /* Undefined. */
  920.                     break ;
  921.       case '+'    : result += disp_val ;         /* Addition. */
  922.                     break ;
  923.       case '-'    : result -= disp_val ;         /* Subtraction. */
  924.                     break ;
  925.       case 'x'    : result *= disp_val ;         /* Multiplication. */
  926.                     break ;
  927.       case '/'    : result /= disp_val ;         /* Division. */
  928.                     break ;
  929.  
  930.       case '&'    : temp = (BOOLEAN) result & (BOOLEAN) disp_val ;   /* AND. */
  931.                     isboolean = 1 ;
  932.                     break ;
  933.       case '|'    : temp = (BOOLEAN) result | (BOOLEAN) disp_val ;   /* OR. */
  934.                     isboolean = 1 ;
  935.                     break ;
  936.       case '^'    : temp = (BOOLEAN) result ^ (BOOLEAN) disp_val ;   /* XOR. */
  937.                     isboolean = 1 ;
  938.                     break ;
  939.       case 'n'    : temp = (BOOLEAN) result ^ (BOOLEAN) disp_val ;   /* XNOR. */
  940.                     temp = ~((BOOLEAN) temp) ;
  941.                     isboolean = 1 ;
  942.                     break ;
  943.       case '='    : break ;                                        /* Equals. */
  944.     }
  945.  
  946.   if (isboolean) result = setbool(temp) ;
  947.   STRCPY(display,make_number(result)) ;
  948.   display_result(display) ;
  949.   if (!(cur_value == '=' && old_cal_value == '=')) last_input = disp_val ;
  950.  
  951.   disp_val = result ;
  952.   if (cur_value != '=') cur_op = cur_value ;
  953.   old_cal_value = cur_value ;
  954.   new_input = 0 ;
  955. }
  956.  
  957.  
  958. do_clear()       /* Clear the calculator display and re-initialise. */
  959.  
  960. {
  961.   clear_display() ;
  962.   initialise() ;
  963. }
  964.  
  965.  
  966. do_close()       /* Close the window to its iconic form. */
  967.  
  968. {
  969.   if ((int) window_get(rframe, WIN_SHOW) == TRUE)
  970.     toggle_reg_canvas() ;
  971.   WINDOW_SET(frame,FRAME_CLOSED,TRUE,0) ;
  972. }
  973.  
  974.  
  975. do_delete()     /* Remove the last numeric character typed. */
  976.  
  977. {
  978.   if (strlen(display)) display[strlen(display)-1] = '\0' ;
  979.   display_result(display) ;
  980.   disp_val = convert_display() ;    /* Convert input to a number. */
  981. }
  982.  
  983. do_help()
  984.  
  985. {
  986.   char help_str[MAXLINE],nextline[MAXLINE],*p ;
  987.   int n,y ;
  988.  
  989.   PANEL_SET(base_item,PANEL_LABEL_STRING,"HLP",0) ;
  990.   n = get_next_value() ;
  991.   display_base(base) ;
  992.  
  993.   WINDOW_SET(canvas,WIN_CURSOR,&help_cursor,0) ;
  994.   pw_writebackground(cpw,0,0,TOTAL_WIDTH,TOTAL_HEIGHT,PIX_CLR) ;
  995.   if (nohelp) make_text(20,20,"No help file found.") ;
  996.   else
  997.     { 
  998.       SPRINTF(help_str,"%%%s%%\n",buttons[n].str) ;
  999.       rewind(hfd) ;
  1000.       while (p = fgets(nextline,BUFSIZ,hfd))
  1001.         if (*p == '%' && EQUAL(p,help_str)) break ;
  1002.       y = 15 ;
  1003.       for (;;)
  1004.         {
  1005.           FGETS(nextline,BUFSIZ,hfd) ;
  1006.           if (EQUAL(nextline,"%%\n")) break ;
  1007.           nextline[strlen(nextline)-1] = '\0' ;
  1008.           make_text(5,y,nextline) ;
  1009.           y += 15 ;
  1010.         }
  1011.     }
  1012.  
  1013.   make_text(5,y+25,DEF_CONT_MSG) ;
  1014.   for (;;)
  1015.     {
  1016.       WINDOW_READ_EVENT(canvas,&event) ;
  1017.       if ((event_is_up(&event) && event_is_button(&event)) ||
  1018.           (event_is_ascii(&event) && event_id(&event))) break ;
  1019.     }
  1020.   make_canvas(0) ;
  1021.   WINDOW_SET(canvas,WIN_CURSOR,main_cursor,0) ;
  1022. }
  1023.  
  1024.  
  1025. do_memory()        /* Store or retrieve number from memory location. */
  1026.  
  1027. {
  1028.   int n,valid ;
  1029.  
  1030.   valid = 0 ;
  1031.   while (!valid)
  1032.     {
  1033.       n = get_next_value() ;
  1034.       if (buttons[n].value >= '0' && buttons[n].value <= '9')
  1035.         {
  1036.           switch (cur_value)
  1037.             {
  1038.               case 'r' : disp_val = mem_vals[char_val(buttons[n].value)] ;
  1039.                          break ;
  1040.               case 's' : mem_vals[char_val(buttons[n].value)] = disp_val ;
  1041.                          make_registers() ;
  1042.             }
  1043.           valid = 1 ;
  1044.         }
  1045.     }    
  1046.   STRCPY(display,make_number(disp_val)) ;
  1047.   display_result(display) ;
  1048. }
  1049.  
  1050.  
  1051. do_not()         /* Do logical NOT operation on current display value. */
  1052.  
  1053. {
  1054.   disp_val = setbool(~((BOOLEAN) disp_val)) ;
  1055.   STRCPY(display,make_number(disp_val)) ;
  1056.   display_result(display) ;
  1057. }
  1058.  
  1059.  
  1060. do_number()
  1061.  
  1062. {
  1063.   int n ;
  1064.   static int maxvals[4] = {1, 7, 9, 15} ;
  1065.  
  1066.   n = cur_value - '0' ;
  1067.   if (base == HEX && cur_value >= 'a' && cur_value <= 'f')
  1068.     n = cur_value - 'a' + 10 ;
  1069.   if (n > maxvals[base]) return ;
  1070.  
  1071.   if (toclear)
  1072.     {
  1073.       SPRINTF(display,"%c",cur_value) ;
  1074.       toclear = 0 ;
  1075.     }
  1076.   else if (strlen(display) < disp_length[base])
  1077.     STRNCAT(display,&cur_value,1) ;
  1078.   make_display(display) ;
  1079.   disp_val = convert_display() ;    /* Convert input to a number. */
  1080.   new_input = 1 ;
  1081. }
  1082.  
  1083.  
  1084. do_point()       /* Handle numeric point. */
  1085.  
  1086. {
  1087.   if (!pointed)
  1088.     {
  1089.       if (toclear)
  1090.         {
  1091.           STRCPY(display,".") ;
  1092.           toclear = 0 ;
  1093.         }
  1094.       else if (strlen(display) < disp_length[base])
  1095.         STRNCAT(display,".",1) ;
  1096.       pointed = 1 ;
  1097.     }
  1098.   make_display(display) ;
  1099.   disp_val = convert_display() ;    /* Convert input to a number. */
  1100. }
  1101.  
  1102.  
  1103. do_quit()        /* Terminate the program. */
  1104.  
  1105. {
  1106.   WINDOW_DESTROY(frame) ;
  1107.   WINDOW_DESTROY(rframe) ;
  1108. }
  1109.  
  1110.  
  1111. do_shift()       /* Shift the display value to the left or the right. */
  1112.  
  1113. {
  1114.   int n,shift,valid ;
  1115.   BOOLEAN temp ;
  1116.  
  1117.   valid = 0 ;
  1118.   while (!valid)
  1119.     {
  1120.       n = get_next_value() ;
  1121.       if (buttons[n].value >= '0' && buttons[n].value <= '9')
  1122.         {
  1123.           shift = char_val(buttons[n].value) ;
  1124.           valid = 1 ;
  1125.         }
  1126.     }
  1127.   temp = (BOOLEAN) convert_display() ;
  1128.   switch (cur_value)
  1129.     {
  1130.       case '<' : temp = temp << shift ;
  1131.                  break ;
  1132.       case '>' : temp = temp >> shift ;
  1133.     }
  1134.   STRCPY(display,make_number(setbool(temp))) ;
  1135.   display_result(display) ;
  1136.   disp_val = last_input = convert_display() ;
  1137. }
  1138.  
  1139.  
  1140. do_sqrt()        /* Square root. */
  1141.  
  1142. {
  1143.   disp_val = sqrt(disp_val) ;
  1144.   STRCPY(display,make_number(disp_val)) ;
  1145.   display_result(display) ;
  1146. }
  1147.  
  1148.  
  1149. double
  1150. setbool(p)
  1151. BOOLEAN p ;
  1152.  
  1153. {
  1154.   BOOLEAN q ;
  1155.   double val ;
  1156.  
  1157.   q = p & 0x80000000 ;
  1158.   p &= 0x7fffffff ;
  1159.   val = (double) p ;
  1160.   if (q) val += 2147483648.0 ;
  1161.   return(val) ;
  1162. }
  1163. Funky_Stuff
  1164. len=`wc -c < functions.c`
  1165. if [ $len !=     9184 ] ; then
  1166. echo error: functions.c was $len bytes long, should have been     9184
  1167. fi
  1168. fi # end of overwriting check
  1169. if [ -f calctool.h ]
  1170. then
  1171. echo shar: will not over-write existing file calctool.h
  1172. else
  1173. echo shar: extracting 'calctool.h',     3213 characters
  1174. cat > calctool.h <<'Funky_Stuff'
  1175.  
  1176. /*  calctool.h
  1177.  *
  1178.  *  This files contains all the definitions used by the calctool program.
  1179.  *
  1180.  *  Copyright (c) Rich Burridge - September 1987.
  1181.  *                Sun Microsystems, Australia - All rights reserved.
  1182.  *
  1183.  *  Includes ideas and code from:
  1184.  *                Rich Baughman, Consumer Financial Institute, Newton, MA
  1185.  *
  1186.  *  Version 1.4.
  1187.  *
  1188.  *  No responsibility is taken for any errors or inaccuracies inherent
  1189.  *  either to the comments or the code of this program, but if
  1190.  *  reported to me then an attempt will be made to fix them.
  1191.  */
  1192.  
  1193. #include <stdio.h>
  1194. #include <strings.h>
  1195. #include <ctype.h>
  1196. #include <math.h>
  1197.  
  1198. #include <suntool/sunview.h>
  1199. #include <suntool/canvas.h>
  1200. #include <suntool/panel.h>
  1201.  
  1202. char *sprintf() ;
  1203.  
  1204. #define  FGETS          (void) fgets     /* To make lint happy. */
  1205. #define  FPRINTF        (void) fprintf
  1206. #define  IOCTL          (void) ioctl
  1207. #define  PANEL_SET      (void) panel_set
  1208. #define  READ           (void) read
  1209. #define  SPRINTF        (void) sprintf
  1210. #define  SSCANF         (void) sscanf
  1211. #define  STRCAT         (void) strcat
  1212. #define  STRCPY         (void) strcpy
  1213. #define  STRNCAT        (void) strncat
  1214. #define  STRNCPY            (void) strncpy
  1215. #define  WINDOW_DESTROY     (void) window_destroy
  1216. #define  WINDOW_READ_EVENT  (void) window_read_event
  1217. #define  WINDOW_SET         (void) window_set
  1218.  
  1219. #define  SMALLFONT      "/usr/lib/fonts/fixedwidthfonts/screen.r.7"
  1220. #define  NORMALFONT     "/usr/lib/fonts/fixedwidthfonts/screen.r.12"
  1221.  
  1222. #define  BIN            0                /* Base definitions. */
  1223. #define  OCT            1
  1224. #define  DEC            2
  1225. #define  HEX            3
  1226.  
  1227. #define  BUTTON_BORDER  5                /* No of pixels in border. */
  1228. #define  BUTTON_COLS    6                /* No of columns of buttons. */
  1229. #define  BUTTON_GAP     5                /* No of pixels between buttons. */
  1230. #define  BUTTON_HEIGHT  22               /* Number of pixels for height. */
  1231. #define  BUTTON_ROWS    7                /* No of rows of buttons. */
  1232. #define  BUTTON_WIDTH   36               /* No of pixels for width. */
  1233. #define  DEF_CONT_MSG   "Hit any key or button to continue."
  1234. #define  DISPLAY        30               /* Calculators numerical display. */
  1235.  
  1236. #define  EQUAL          !strcmp          /* For character comparisons. */
  1237. #define  EXTRA          5                /* Extra useful character definitions. */
  1238. #define  HELPNAME       "calctool.help"
  1239. #define  MAX_DIGITS     32               /* Maximum displayable number of digits. */
  1240. #define  MAXLINE        80               /* Length of character strings. */
  1241. #define  MAXREGS        10               /* Maximum number of memory registers. */
  1242. #define  MIN(x,y)       ((x) < (y) ? (x) : (y))
  1243. #define  NOBUTTONS      BUTTON_ROWS * BUTTON_COLS
  1244. #define  TOTAL_HEIGHT   (BUTTON_ROWS * BUTTON_HEIGHT) + \
  1245.                         ((BUTTON_ROWS - 1) * BUTTON_GAP) + (2 * BUTTON_BORDER)
  1246. #define  TOTAL_ITEMS    NOBUTTONS + EXTRA    /* Total number of definitions. */
  1247. #define  TOTAL_WIDTH    (BUTTON_COLS * BUTTON_WIDTH) + \
  1248.                         ((BUTTON_COLS - 1) * BUTTON_GAP) + (2 * BUTTON_BORDER)
  1249.  
  1250. typedef  unsigned long  BOOLEAN ;
  1251.  
  1252. struct button {
  1253.          char *str ;
  1254.          int  (*func)() ;
  1255.          char value ;
  1256. } ;
  1257. Funky_Stuff
  1258. len=`wc -c < calctool.h`
  1259. if [ $len !=     3213 ] ; then
  1260. echo error: calctool.h was $len bytes long, should have been     3213
  1261. fi
  1262. fi # end of overwriting check
  1263. if [ -f patchlevel.h ]
  1264. then
  1265. echo shar: will not over-write existing file patchlevel.h
  1266. else
  1267. echo shar: extracting 'patchlevel.h',       23 characters
  1268. cat > patchlevel.h <<'Funky_Stuff'
  1269. #define  PATCHLEVEL  1
  1270. Funky_Stuff
  1271. len=`wc -c < patchlevel.h`
  1272. if [ $len !=       23 ] ; then
  1273. echo error: patchlevel.h was $len bytes long, should have been       23
  1274. fi
  1275. fi # end of overwriting check
  1276. if [ -f button.icon ]
  1277. then
  1278. echo shar: will not over-write existing file button.icon
  1279. else
  1280. echo shar: extracting 'button.icon',     1933 characters
  1281. cat > button.icon <<'Funky_Stuff'
  1282. /* Format_version=1, Width=64, Height=64, Depth=1, Valid_bits_per_item=16
  1283.  */
  1284.     0x1FFF,0xFFFF,0x0000,0x0000,0x3FFF,0xFFFF,0x8000,0x0000,
  1285.     0x6000,0x0000,0xC000,0x0000,0xC000,0x0000,0xE000,0x0000,
  1286.     0xCFFF,0xFFFF,0x6000,0x0000,0xC800,0x0002,0xE000,0x0000,
  1287.     0xC800,0x0003,0x6000,0x0000,0xC800,0x0002,0xE000,0x0000,
  1288.     0xC800,0x0003,0x6000,0x0000,0xC800,0x0002,0xE000,0x0000,
  1289.     0xC800,0x0003,0x6000,0x0000,0xC800,0x0002,0xE000,0x0000,
  1290.     0xC800,0x0003,0x6000,0x0000,0xC800,0x0002,0xE000,0x0000,
  1291.     0xC800,0x0003,0x6000,0x0000,0xC800,0x0002,0xE000,0x0000,
  1292.     0xC800,0x0003,0x6000,0x0000,0xCFFF,0xFFFE,0xE000,0x0000,
  1293.     0xD555,0x5555,0x6000,0x0000,0x6AAA,0xAAAA,0xC000,0x0000,
  1294.     0x3FFF,0xFFFF,0x8000,0x0000,0x1FFF,0xFFFF,0x0000,0x0000,
  1295.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1296.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1297.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1298.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1299.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1300.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1301.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1302.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1303.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1304.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1305.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1306.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1307.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1308.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1309.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1310.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1311.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1312.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1313.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1314.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,
  1315.     0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000
  1316. Funky_Stuff
  1317. len=`wc -c < button.icon`
  1318. if [ $len !=     1933 ] ; then
  1319. echo error: button.icon was $len bytes long, should have been     1933
  1320. fi
  1321. fi # end of overwriting check
  1322. if [ -f calctool.icon ]
  1323. then
  1324. echo shar: will not over-write existing file calctool.icon
  1325. else
  1326. echo shar: extracting 'calctool.icon',     1933 characters
  1327. cat > calctool.icon <<'Funky_Stuff'
  1328. /* Format_version=1, Width=64, Height=64, Depth=1, Valid_bits_per_item=16
  1329.  */
  1330.     0x1555,0x5555,0x5540,0x0000,0x2AAA,0xAAAA,0xAA80,0x0000,
  1331.     0x5555,0x5555,0x5540,0x0000,0xFFFF,0xFFFF,0xFE80,0x0000,
  1332.     0x8000,0x0000,0x0340,0x0000,0xBFFF,0xFFFF,0xFA80,0x0000,
  1333.     0xA000,0x0000,0x0B40,0x0000,0xA000,0x0000,0x0A80,0x0000,
  1334.     0xA600,0x2082,0x0B40,0x0000,0xA900,0x6186,0x0A80,0x0000,
  1335.     0xA200,0x2282,0x0B40,0x0000,0xA100,0x23C2,0x0A80,0x0000,
  1336.     0xA908,0x2082,0x0B40,0x0000,0xA608,0x7087,0x0A80,0x0000,
  1337.     0xA000,0x0000,0x0B40,0x0000,0xA000,0x0000,0x0A80,0x0000,
  1338.     0xBFFF,0xFFFF,0xFB40,0x0000,0x8000,0x0000,0x0280,0x0000,
  1339.     0x8000,0x0000,0x0340,0x0000,0xBFDF,0xEFF7,0xFA80,0x0000,
  1340.     0xA050,0x2814,0x0B40,0x0000,0xAF53,0x2994,0x0A80,0x0000,
  1341.     0xA154,0xAA55,0x1340,0x0000,0xA253,0x2A54,0xAA80,0x0000,
  1342.     0xA254,0xA9D4,0x4B40,0x0000,0xA454,0xA854,0xAA80,0x0000,
  1343.     0xA453,0x2995,0x1B40,0x0000,0xA050,0x2814,0x0A80,0x0000,
  1344.     0xBFDF,0xEFF7,0xFB40,0x0000,0x8000,0x0000,0x0280,0x0000,
  1345.     0xBFDF,0xEFF7,0xFB40,0x0000,0xA050,0x2814,0x0A80,0x0000,
  1346.     0xA257,0xA994,0x2B40,0x0000,0xA654,0x2A14,0x4A80,0x0000,
  1347.     0xAA57,0x2B94,0x4B40,0x0000,0xAF50,0xAA54,0x8A80,0x0000,
  1348.     0xA254,0xAA54,0x8B40,0x0000,0xA253,0x2995,0x0A80,0x0000,
  1349.     0xA050,0x2814,0x0B40,0x0000,0xBFDF,0xEFF7,0xFA80,0x0000,
  1350.     0x8000,0x0000,0x0340,0x0000,0xBFDF,0xEFF7,0xFA80,0x0000,
  1351.     0xA050,0x2814,0x0B40,0x0000,0xA253,0x2994,0x0A80,0x0000,
  1352.     0xA654,0xAA54,0x0B40,0x0000,0xA250,0xA895,0xEA80,0x0000,
  1353.     0xA253,0x2854,0x0B40,0x0000,0xA254,0x2A54,0x0A80,0x0000,
  1354.     0xA757,0xA994,0x0B40,0x0000,0xA050,0x2814,0x0A80,0x0000,
  1355.     0xBFDF,0xEFF7,0xFB40,0x0000,0x8000,0x0000,0x0280,0x0000,
  1356.     0xBFDF,0xEFF7,0xFB40,0x0000,0xA050,0x2814,0x0A80,0x0000,
  1357.     0xA650,0x2814,0x0B40,0x0000,0xA950,0x2814,0x4A80,0x0000,
  1358.     0xAB50,0x2BD4,0x4B40,0x0000,0xAD50,0x2815,0xFA80,0x0000,
  1359.     0xA951,0x2BD4,0x4B40,0x0000,0xA651,0x2814,0x4A80,0x0000,
  1360.     0xA050,0x2814,0x0B40,0x0000,0xBFDF,0xEFF7,0xFA80,0x0000,
  1361.     0x8000,0x0000,0x0300,0x0000,0xFFFF,0xFFFF,0xFE00,0x0000
  1362. Funky_Stuff
  1363. len=`wc -c < calctool.icon`
  1364. if [ $len !=     1933 ] ; then
  1365. echo error: calctool.icon was $len bytes long, should have been     1933
  1366. fi
  1367. fi # end of overwriting check
  1368. if [ -f help.cursor ]
  1369. then
  1370. echo shar: will not over-write existing file help.cursor
  1371. else
  1372. echo shar: extracting 'help.cursor',      193 characters
  1373. cat > help.cursor <<'Funky_Stuff'
  1374. /* Format_version=1, Width=16, Height=16, Depth=1, Valid_bits_per_item=16
  1375.  */
  1376.     0xFFFF,0x8001,0xBFFD,0xA1C5,0xA225,0xA225,0xA025,0xA045,
  1377.     0xA085,0xA085,0xA005,0xA085,0xA085,0xBFFD,0x8001,0xFFFF
  1378. Funky_Stuff
  1379. len=`wc -c < help.cursor`
  1380. if [ $len !=      193 ] ; then
  1381. echo error: help.cursor was $len bytes long, should have been      193
  1382. fi
  1383. fi # end of overwriting check
  1384. if [ -f calctool.help ]
  1385. then
  1386. echo shar: will not over-write existing file calctool.help
  1387. else
  1388. echo shar: extracting 'calctool.help',     5668 characters
  1389. cat > calctool.help <<'Funky_Stuff'
  1390. %<<%
  1391. Left shift n                ( < ).
  1392.  
  1393. This must be followed by a digit
  1394. in the range 0 to 9 to indicate
  1395. how many places to shift.
  1396. %%
  1397.  
  1398. %BIN%
  1399. Change base to binary       ( B ).
  1400.  
  1401. The display value is shown in
  1402. binary. A maximum of 32 digits
  1403. are allowed.
  1404. %%
  1405.  
  1406. %OCT%
  1407. Change base to octal        ( O ).
  1408.  
  1409. The display value is shown in
  1410. octal. A maximum of 15 digits
  1411. are allowed.
  1412. %%
  1413.  
  1414. %DEC%
  1415. Change base to decimal      ( D ).
  1416.  
  1417. The display value is shown in
  1418. decimal. This is the default
  1419. base. A maximum of 12 digits
  1420. are allowed.
  1421. %%
  1422.  
  1423. %HEX%
  1424. Change base to hexidecimal  ( H ).
  1425.  
  1426. The display value is shown in
  1427. hexidecimal. A maximum of 12
  1428. digits are allowed.
  1429. %%
  1430.  
  1431. %>>%
  1432. Right shift n               ( > ).
  1433.  
  1434. This must be followed by a digit
  1435. in the range 0 to 9 to indicate
  1436. how many places to shift.
  1437. %%
  1438.  
  1439. %STO%
  1440. Store memory register n     ( s ).
  1441.  
  1442. This must be followed by a digit
  1443. in the range 0 to 9 to indicate
  1444. which memory register to store
  1445. the current display value in.
  1446. %%
  1447.  
  1448. %RCL%
  1449. Retrieve memory register n  ( r ).
  1450.  
  1451. This must be followed by a digit
  1452. in the range 0 to 9 to indicate
  1453. which memory register to retrieve
  1454. the value from.
  1455. %%
  1456.  
  1457. % D %
  1458. Hex D (decimal 13)          ( d ).
  1459.  
  1460. This selection is only valid if
  1461. the current base is hexidecimal.
  1462. %%
  1463.  
  1464. % E %
  1465. Hex E (decimal 14)          ( e ).
  1466.  
  1467. This selection is only valid if
  1468. the current base is hexidecimal.
  1469. %%
  1470.  
  1471. % F %
  1472. Hex F (decimal 15)          ( f ).
  1473.  
  1474. This selection is only valid if
  1475. the current base is hexidecimal.
  1476. %%
  1477.  
  1478. %CLR%
  1479. Clear display          ( DELETE ).
  1480.  
  1481. This will clear the value of the
  1482. calculators display.
  1483. %%
  1484.  
  1485. %NOT%
  1486. Logical NOT                 ( ~ ).
  1487.  
  1488. This operation will perform the
  1489. logical NOT operation of the
  1490. current value of the calculators
  1491. display.
  1492. %%
  1493.  
  1494. %SQR%
  1495. Square root                 ( S ).
  1496.  
  1497. This operation will perform a
  1498. square root operation on the
  1499. current value of the calculator
  1500. display.
  1501. %%
  1502.  
  1503. % A %
  1504. Hex A (decimal 10)          ( a ).
  1505.  
  1506. This selection is only valid if
  1507. the current base is hexidecimal.
  1508. %%
  1509.  
  1510. % B %
  1511. Hex B (decimal 11)          ( b ).
  1512.  
  1513. This selection is only valid if
  1514. the current base is hexidecimal.
  1515. %%
  1516.  
  1517. % C %
  1518. Hex C (decimal 12)          ( c ).
  1519.  
  1520. This selection is only valid if
  1521. the current base is hexidecimal.
  1522. %%
  1523.  
  1524. %BSP%
  1525. Erase character     ( BACKSPACE ).
  1526.  
  1527. The right most character of the
  1528. current calculator display value
  1529. is removed, and the value of the
  1530. display is recalculated. Note,
  1531. internal accuracy is lost with
  1532. this operation.
  1533. %%
  1534.  
  1535. %AND%
  1536. Logical AND                 ( & ).
  1537.  
  1538. This operation takes the last
  1539. number and the next number
  1540. entered, and performs a logical
  1541. AND operation on them, treating
  1542. both numbers as unsigned long
  1543. integers.
  1544. %%
  1545.  
  1546. %OR%
  1547. Logical OR                  ( | ).
  1548.  
  1549. This operation takes the last
  1550. number and the next number
  1551. entered, and performs a logical
  1552. OR operation on them, treating
  1553. both numbers as unsigned long
  1554. integers.
  1555. %%
  1556.  
  1557. % 7 %
  1558. Numeric 7                   ( 7 ).
  1559.  
  1560. This selection is ignored if
  1561. the current base is binary.
  1562. %%
  1563.  
  1564. % 8 %
  1565. Numeric 8                   ( 8 ).
  1566.  
  1567. This selection is ignored if
  1568. the current base is octal or
  1569. binary.
  1570. %%
  1571.  
  1572. % 9 %
  1573. Numeric 9                   ( 9 ).
  1574.  
  1575. This selection is ignored if
  1576. the current base is octal or
  1577. binary.
  1578. %%
  1579.  
  1580. % X %
  1581. Multiplication    ( * or x or X ).
  1582.  
  1583. This operation takes the last
  1584. number and the next number
  1585. entered, and performs an
  1586. arithmetic multiplication on
  1587. them.
  1588. %%
  1589.  
  1590. %XOR%
  1591. Logical XOR                 ( ^ ).
  1592.  
  1593. This operation takes the last
  1594. number and the next number
  1595. entered, and performs a logical
  1596. XOR operation on them, treating
  1597. both numbers as unsigned long
  1598. integers.
  1599. %%
  1600.  
  1601. %XNR%
  1602. Logical XNOR           ( n or N ).
  1603.  
  1604. This operation takes the last
  1605. number and the next number
  1606. entered, and performs a logical
  1607. XNOR operation on them, treating
  1608. both numbers as unsigned long
  1609. integers.
  1610. %%
  1611.  
  1612. % 4 %
  1613. Numeric 4                   ( 4 ).
  1614.  
  1615. This selection is ignored if
  1616. the current base is binary.
  1617. %%
  1618.  
  1619. % 5 %
  1620. Numeric 5                   ( 5 ).
  1621.  
  1622. This selection is ignored if
  1623. the current base is binary.
  1624. %%
  1625.  
  1626. % 6 %
  1627. Numeric 6                   ( 6 ).
  1628.  
  1629. This selection is ignored if
  1630. the current base is binary.
  1631. %%
  1632.  
  1633. % / %
  1634. Division                    ( / ).
  1635.  
  1636. This operation takes the last
  1637. number and performs an
  1638. arithemetic division by the
  1639. next number entered.
  1640. %%
  1641.  
  1642. %ACC%
  1643. Accuracy n                  ( A ).
  1644.  
  1645. This must be followed by a digit
  1646. in the range 0 to 9 to indicate
  1647. how many digits of precision are
  1648. to be displayed.
  1649. %%
  1650.  
  1651. %HLP%
  1652. Calctool Help v1.4.         ( ? ).
  1653.  
  1654. All calculations performed as
  1655. doubles. The display can be used
  1656. with the GET and PUT function keys
  1657. with other Sunview windows. right
  1658. mouse button toggles button display
  1659. with keyboard equivalents. Middle
  1660. button toggles register display.
  1661.  
  1662. For furthur help, select HLP and
  1663. another selection.
  1664. %%
  1665.  
  1666. % 1 %
  1667. Numeric 1                   ( 1 ).
  1668. %%
  1669.  
  1670. % 2 %
  1671. Numeric 2                   ( 2 ).
  1672.  
  1673. This selection is ignored if
  1674. the current base is binary.
  1675. %%
  1676.  
  1677. % 3 %
  1678. Numeric 3                   ( 3 ).
  1679.  
  1680. This selection is ignored if
  1681. the current base is binary.
  1682. %%
  1683.  
  1684. % - %
  1685. Subtraction                 ( - ).
  1686.  
  1687. This operation takes the last
  1688. number and performs an
  1689. arithemetic subtraction of the
  1690. next number entered.
  1691. %%
  1692.  
  1693. %OFF%
  1694. Turn calctool iconic      ( ESC ).
  1695.  
  1696. This operation is ignored if
  1697. not a Sun Tool.
  1698. %%
  1699.  
  1700. %END%
  1701. Quit calctool          ( q or Q ).
  1702.  
  1703. The calctool program is exited.
  1704. %%
  1705.  
  1706. % 0 %
  1707. Numeric 0                   ( 0 ).
  1708. %%
  1709.  
  1710. % . %
  1711. Numeric point               ( . ).
  1712.  
  1713. Selecting this starts the
  1714. fractional part of the numeric
  1715. entry.
  1716. %%
  1717.  
  1718. % = %
  1719. Calculate result  ( = or RETURN ).
  1720.  
  1721. The result of the current
  1722. calculation is displayed in
  1723. the current base.
  1724. %%
  1725.  
  1726. % + %
  1727. Addition                    ( + ).
  1728.  
  1729. This operation takes the last
  1730. number and the next number
  1731. entered, and performs an
  1732. arithmetic addition on them.
  1733. %%
  1734. Funky_Stuff
  1735. len=`wc -c < calctool.help`
  1736. if [ $len !=     5668 ] ; then
  1737. echo error: calctool.help was $len bytes long, should have been     5668
  1738. fi
  1739. fi # end of overwriting check
  1740.