home *** CD-ROM | disk | FTP | other *** search
- ' +===========================================+
- ' | LSRGCALC.BAS |
- ' | "LS-1.0 Plus Scientific Calculator" |
- ' | Version 1.0 |
- ' | Written and Developed by |
- ' | Lawrence Stone |
- ' | Copyright (C) 1990 |
- ' | Lawrence Stone Research Group |
- ' +-------------------------------------------+
-
- ' +===========================================+
- ' | Purpose: TSR pop-up calculator |
- ' +-------------------------------------------+
-
- ' +===========================================+
- ' | Pre-processor |
- ' +-------------------------------------------+
-
- '#LinkSwitches: '/noe/exe'
- '#CompileSwitches: '/FPi/Ot/S/X/O'
- '#EXEName: 'LSRGCALC'
- '#LeadingObject: 'd:\qb\obj\STAYQB4'
- '#TrailingObject: 'f:\CALCMOD'
- '#TrailingObject: 'd:\qb\obj\MHGETCHR'
- '#TrailingObject: 'd:\bc7\lib\SMALLERR'
- '#TrailingObject: 'd:\qb\qbpro\pro7\obj\XREDIR70'
- '#TrailingObject: 'd:\qb\obj\MHMISCP'
- '#Libraries: 'd:\qb\bin\MHLIB2'
- '#Libraries: 'd:\qb\bin\MHPRO1'
- '#Libraries: 'd:\qb\bin\MHPRO2'
- '#Libraries: 'd:\qb\bin\MHPRO4'
- '#Libraries: 'd:\qb\bin\MHPRO7'
- '#ObjectPath: 'F:'
- '#EXEpath: 'F:'
- '#WorkPath: 'F:'
-
- ' ============================================================================
- ' Subprogram and Function Declarations Go Here (If using QB4 / BC6)
- ' ----------------------------------------------------------------------------
-
- DECLARE SUB Complex2String (a AS ANY, x$)
- DECLARE SUB ComplexAdd (a AS ANY, b AS ANY, c AS ANY)
- DECLARE SUB ComplexDiv (a AS ANY, b AS ANY, c AS ANY, Ecode%)
- DECLARE SUB ComplexExp (a AS ANY, c AS ANY, Ecode%)
- DECLARE SUB ComplexLog (a AS ANY, c AS ANY, Ecode%)
- DECLARE SUB ComplexMul (a AS ANY, b AS ANY, c AS ANY, Ecode%)
- DECLARE SUB ComplexPower (a AS ANY, b AS ANY, c AS ANY, t AS ANY, t1 AS ANY, t2 AS ANY, Ecode%)
- DECLARE SUB ComplexReciprocal (a AS ANY, c AS ANY, t3 AS ANY, Ecode%)
- DECLARE SUB ComplexRoot (a AS ANY, b AS ANY, c AS ANY, t AS ANY, t1 AS ANY, t2 AS ANY, t3 AS ANY, Ecode%)
- DECLARE SUB ComplexSub (a AS ANY, b AS ANY, c AS ANY)
- DECLARE SUB ComplxIntRoot (a AS ANY, c AS ANY, Root!, Ecode%)
- DECLARE SUB ConvertNum (num#, DispNum$, hexOn%, octOn%)
- DECLARE SUB DoShowRed ()
- DECLARE SUB FixDisplay ()
- DECLARE SUB GetKeysRowCol (scanCode%, Row%, Col%)
- DECLARE SUB HiLowSounds ()
- DECLARE SUB InverseVideo (Row%, Col%, Monitor%)
- DECLARE SUB KeyResponce (scanCode%, asci%, shiftStat%)
- DECLARE SUB MainMenu (GoSleep%, terminate%, Row%, Col%, Monitor%, CalcFunction%, tableOn%, hstOn%)
- DECLARE SUB ProcessTable (Operation%, choice%, maxTable%)
- DECLARE SUB ProcessTheHit (Row%, Col%, GoSleep%, terminate%)
- DECLARE SUB RandShuffle (RandArray&())
- DECLARE SUB ResetOperators ()
- DECLARE SUB ScrLine (Lin$, Row%, Col%, Clr%)
- DECLARE SUB ScrollHistory ()
- DECLARE SUB SelectMathOp ()
- DECLARE SUB ShowHist (temp$)
- DECLARE SUB ShowIndicators ()
- DECLARE SUB ShowNumber ()
- DECLARE SUB String2Complex (x$, a AS ANY, Ecode%)
- DECLARE SUB StuffKey (stuff$)
- DECLARE SUB TickPause (Ticks%)
-
- DECLARE FUNCTION ArithMean# (StatArray#())
- DECLARE FUNCTION BinToStr$ (Bin%)
- DECLARE FUNCTION Combinations# (items#, rate#)
- DECLARE FUNCTION DateDiff& (D0$, D1$)
- DECLARE FUNCTION DayShort$ (Day%)
- DECLARE FUNCTION DayMath$ (D0$, Days&)
- DECLARE FUNCTION DayOfWeek% (Month%, Day%, Year%)
- DECLARE FUNCTION FloatNum# (DispNum$)
- DECLARE FUNCTION FromJulian$ (JulianNumber&)
- DECLARE FUNCTION FromSeconds$ (Seconds&)
- DECLARE FUNCTION GeoMean# (StatArray#())
- DECLARE FUNCTION GoodDate% (dat$)
- DECLARE FUNCTION HarmMean# (StatArray#())
- DECLARE FUNCTION HoursMath$ (T0$, Hours!)
- DECLARE FUNCTION MinutesMath$ (T0$, Minutes!)
- DECLARE FUNCTION MonthLong$ (Month%)
- DECLARE FUNCTION MonthMath$ (D0$, Months&)
- DECLARE FUNCTION Permutations# (items#, rate#)
- DECLARE FUNCTION QuadMean# (StatArray#())
- DECLARE FUNCTION Rand& (RandArray&())
- DECLARE FUNCTION RandExp# (mean#, RandArray&())
- DECLARE FUNCTION RandFrac! (RandArray&())
- DECLARE FUNCTION RandNormal# (mean#, stdDev#, RandArray&())
- DECLARE FUNCTION RandRange# (num1#, num2#, RandArray&())
- DECLARE FUNCTION Round# (N#, decimal%)
- DECLARE FUNCTION SecondsMath$ (T0$, Seconds&)
- DECLARE FUNCTION StrToBin% (b$)
- DECLARE FUNCTION TimeDiff$ (T0$, t1$)
- DECLARE FUNCTION ToJulian& (D0$)
- DECLARE FUNCTION ToSeconds& (T0$)
- DECLARE FUNCTION YearMath$ (D0$, Years&)
-
- TYPE Complex
- r AS SINGLE
- i AS SINGLE
- END TYPE
-
- DEFINT A-Z
-
- '--------------------------------------------------------------------
- 'Defining Your Hot Key - Refer to Appendix A of the Stay-Res manual
- ' for the proper values of Kscan% and Kshift%.
- '--------------------------------------------------------------------
-
- Kscan% = 57 'Define a Hot Key of Right Shift plus Spacebar
- Kshift% = 1
-
- '---------------------------------------------------------------------
- 'Dynamic Arrays Note: because we use SrAutoSetBlock, we will use
- ' this section to define as much as possible. -LS
- '---------------------------------------------------------------------
-
- ' ---- Define the data segment for screen writes.
- REM $DYNAMIC
- DIM CalcScrn%(5632) ' 11,264 bytes of memory is reserved
- DIM Windmem%(4000) ' 8,000 bytes reserved for orig screen
-
- ' ---- Background screen arrays needed for holding the original screen
- ' at the right side of each calculator screen. These arrays provide
- ' smooth animation.
- '
- ' Note that because this TSR could pop-up over a variety of
- ' screen (text) modes at any time, we must dimension our arrays
- ' to handle the largest text screen possible which is 80 x 50.
- '
- ' Array calculation: area% = ((lastCol - startCol) + 1) * 50
- ' area 41 = 2000 ' area% = ((80 - 41) + 1) * 50
- ' area 42 = 1950 ' area% = ((80 - 42) + 1) * 50
- ' area 59 = 1100 ' area% = ((80 - 59) + 1) * 50
-
- DIM Area41%(2000) ' The calculator is closed.
- DIM Area42%(1950) ' The calculator half open.
- DIM Area59%(1100) ' The calculator 3/4 open.
-
- DIM SHARED TheScreen%(4001) ' Used to hold right side of calc when
- ' lookup table is covering it.
-
- ' ---- Statistics array and Random Table array
- DIM SHARED StatArray#(500), RandArray&(1 TO 100)
-
- ' ---- Keystroke History Log and the calculator Table array
- DIM SHARED HistLog(1 TO 100) AS STRING * 29
- DIM SHARED CalcTable(1 TO 512) AS STRING * 29
- REM $STATIC
-
- ' Establish array for Row & column coordinates to calculator functions.
- DIM SHARED CalOps%(7 TO 23, 10 TO 70)
-
- ' ---- Establish various arrays to handle parenthesis operations
- DIM SHARED parenNum1#(1 TO 8), parenMath%(1 TO 8), parenNum2#(1 TO 8)
-
- ' ---- Set various aliases for the Complex TYPE
- DIM SHARED a AS Complex, b AS Complex, c AS Complex, t AS Complex
- DIM SHARED t1 AS Complex, t2 AS Complex, t3 AS Complex
-
- DIM SHARED maxTable%, Monitor%, CalcFunction AS INTEGER, scrolPos%
- DIM SHARED false AS INTEGER, true AS INTEGER, zero AS INTEGER, hstBound
- DIM SHARED hexOn AS INTEGER, binOn AS INTEGER, octOn AS INTEGER
- DIM SHARED degOn AS INTEGER, complxOn AS INTEGER, statsOn AS INTEGER
- DIM SHARED dateOn AS INTEGER, timeOn AS INTEGER, lptOn AS INTEGER
- DIM SHARED diskFile AS INTEGER, realNum AS INTEGER, parens AS INTEGER
- DIM SHARED fixedPoint AS INTEGER, hstOn AS INTEGER, memOn AS INTEGER
- DIM SHARED radOn AS INTEGER, gradOn AS INTEGER, makedate AS INTEGER
- DIM SHARED makeArray%, DosBusy%, makePower%, makeRoot%, Power$, Root$
- DIM SHARED PermComb%, stdDev#, decimal%, mean#, items#, UserError%
- DIM SHARED makeNum%, setValue%, num#, num1#, num2#, N#, mathOp AS INTEGER
-
- DIM SHARED fixedFlag$, LogN$, rate$, DispNumber$, hstCount AS INTEGER
- DIM SHARED PowerFlag$, RootFlag$, Root1$, makeHr$, DispNum$, ProgName$
- DIM SHARED Root2$, goof$, makeYr$, makeMo$, makeDy$, dateDisp$, CalcDisp$
- DIM SHARED makeMin$, makeSec$, mean$, stdDev$, DosBusy$, timeDisp$
- DIM SHARED OutPutFile$, cmmd$, stuff$, LogBaseN$, tableOn, screenArea%
- DIM SHARED CaptureLog0$, CaptureLog1$, CaptureLog2$, arcOn%, hypOn%
-
- CONST pi# = 3.141592653589#, L10# = 2.30258509299405#
- CONST angFactor# = 57.2957795130823#
-
- ' ---- Define the program's name.
- ProgName$ = "LSRGCALC"
-
- ' ---- Define a string to inform the user what the hot keys are
- HotKeys$ = "Use <Right Shift> + <SpaceBar> Key Combination to Awaken."
-
- false = 0: true = NOT false: zero = false
- degOn = true: realNum = true
-
- fixedPoint = true: fixedFlag$ = "Fixed = ": LogN$ = "Base n = "
- PowerFlag$ = "Power = ": RootFlag$ = "Root = ": Root1$ = "r√ = "
- Root2$ = "j√ = ": goof$ = " Error": makeYr$ = "Years = "
- makeMo$ = "Months = ": makeDy$ = "Days = ": rate$ = "Rate = "
- ProgTerminate$ = " - Program Terminated!": makeHr$ = "Hours = "
- makeMin$ = "Minutes = ": makeSec$ = "Seconds = ": mean$ = "ñ = "
- stdDev$ = "sd = ": DosBusy$ = "DOS is Busy" + SPACE$(14)
- OutPutFile$ = ProgName$ + ".FIL" + CHR$(0)
-
- ' ---- Set a fixed length string for displaying the keyed numbers
- DispNumber$ = SPACE$(25)
-
- ' ---- Define a string for the date and time template
- dateDisp$ = "mm/dd/yyyy": timeDisp$ = "hh:mm:ss"
-
- ' ---- Have this program reserve a block of DOS memory and have it
- ' contiguous - starting at the top of QB's stack address.
-
- HeapMem& = FRE(-1)
- HeapMem& = HeapMem& - (4096)
- MemNeeded& = SETMEM(-HeapMem&)
-
- CALL SrAutoSetBlock(Paragraphs%, Ecode%)
-
- IF HeapMem& < 65536 OR Ecode% <> zero THEN
- ScrLine SPACE$(2000), 1, 1, 7
- ScrLine "Not enough memory to run " + ProgName$ + ".", 1, 1, 7
- ScrLine "Execution of " + ProgName$ + " terminated.", 2, 1, 7
- HiLowSounds
- END
- END IF
-
- '---------------------------------------------------------------------
- 'Set Up Automatic Screen Save/Restore Parameters
- '---------------------------------------------------------------------
-
- ' ---- Don't use StayRes automatic screen save option - we will be
- ' handling all screen save/restore ourselves.
- Bytes% = 0
- CALL SrUseDynScreenMem(Bytes%)
- CALL SrDontRestoreScreen
-
- '---------------------------------------------------------------------
- 'Stay-Res Plus Options
- '---------------------------------------------------------------------
-
- ' ---- Get the command line argument.
- Lin$ = SPACE$(128)
- CALL MhCommand(Lin$, Length%)
- cmmd$ = UCASE$(LEFT$(Lin$, Length%))
-
- IF cmmd$ = "DISK" THEN
- UseDiskSwap% = -1
- ELSEIF cmmd$ = "DOS" THEN
- DontUseEMS = -1
- ELSEIF cmmd$ <> "EMS" THEN
- cmmd$ = ""
- GOTO InitParams 'Program loaded without options so skip to InitParams
- END IF
-
- ' ---- Check to see if LSRGCALC is already installed.
- IDNumber = 7667
- CALL SrSetId(ProgName$, IDNumber, Ecode)
- IF Ecode THEN
- ScrLine SPACE$(2000), 1, 1, 7
- ScrLine ProgName$ + " Already Installed in Memory.", 1, 1, 7
- ScrLine HotKeys$, 2, 1, 7
- HiLowSounds
- END
- END IF
-
- ' ---- Set the File's initials to "C1".
- Initials$ = "C1"
- CALL SrSetFileInitials(Initials$)
-
- IF UseDiskSwap% THEN 'User requested Disk Swapping
- CALL SrForceFile0 'Allow only two swap files to accumalate
- CALL SrDiskSwap("", Ecode%)
- IF Ecode% THEN
- ScrLine SPACE$(2000), 1, 1, 7
- ScrLine ProgName$ + " Error" + STR$(SwapEcode%) + " During Disk-Swapping Initialization!", 1, 1, 7
- HiLowSounds
- END
- END IF
- ELSE
- IF DontUseEMS THEN 'User requested DOS RAM-residency
- CALL SrIgnoreEMS
- ELSE 'User requested EMS swapping
- CALL SrCheckEMS(Ecode%)
- IF Ecode% THEN
- ScrLine SPACE$(2000), 1, 1, 7
- ScrLine "EMS Memory not available. Using DOS Memory.", 1, 1, 7
- HiLowSounds
- TickPause 36
- END IF
- END IF
- END IF
-
-
- ' ============================================================================
- ' Initialization Section 2 - Your program can use this section to set up all
- ' of its constants, dimension any STATIC arrays
- ' it will need and perform any processing that is
- ' needed before entering the main program logic.
- ' DO NOT delete the "GOSUB BecomeResident" below.
- '
- ' Note: because SrAutoSetBlock was used in lieu
- ' of SrSetBlock, dimensioning static arrays and
- ' constants was already performed. Hence, this
- ' section is only used to perform any processing
- ' needed before entering the main program logic. -LS
- ' ----------------------------------------------------------------------------
-
- InitParams:
- ' ---- Get the screen paramaters
- GOSUB ScreenParams
-
- ' ---- Initialize the random table
- RandShuffle RandArray&()
-
- ' ---- Just in case we're dealing with a weird screen mode
- IF screenArea > 8000 THEN END
-
- ' ---- Open the calculator's appropriate screen file for reading.
- CALL MhFile(zero, CalcScrn$ + CHR$(zero), zero, zero, Handle%, Ecode%)
- IF Ecode% GOTO Handler
-
- ' ---- Read the calc screen directly into the CalcScrn%() array
- Operation% = zero
- Offset% = zero: Bytes% = 11 * 1024
- Dtaseg% = VARSEG(CalcScrn%(zero))
- CALL MhRwSub(Handle%, Operation%, RwPointer&, Dtaseg%, Offset%, Bytes%, Ecode%)
- IF Ecode% GOTO Handler
- CALL MhFile(zero, "", zero, zero, Handle%, Ecode%) 'Close this file.
-
- '---- Open and read the Table file into the table array
- Lin$ = SPACE$(512)
- temp$ = ProgName$ + ".TBL" + CHR$(0)
-
- FOR i% = 1 TO 512 'Input up to 512 lines from the file
- CALL MhLineInput(temp$, Lin$, Length%, Ecode%)
- IF Ecode% THEN EXIT FOR
- maxTable% = i%
- LSET CalcTable(i%) = LEFT$(Lin$, Length%) 'Put it into the array
- NEXT
-
- temp$ = "": Lin$ = ""
- CALL MhCloseFile 'Close this file
-
- '---- Build the array that correlates function numbers to row/col location
- GOSUB BuildArray
-
- ' ---- Inform the user that we are now memory resident and going to sleep.
- IF cmmd$ <> "" THEN
- ScrLine SPACE$(2000), 1, 1, 7
- ScrLine ProgName$ + " is Loaded into Memory and is Going to Sleep.", 1, 1, 7
- ScrLine HotKeys$, 2, 1, 7
- END IF
-
- ' ---- Turn off snow checking for faster video display.
- CALL MhVideo(&HFFFF)
-
- ' ---- Initialize the mouse.
- CALL MhMouseReset(sn1%, sn2%)
-
- IF cmmd$ = "" THEN 'If program was loaded without options...
- GOSUB GetCursorPosition
- Visible% = false 'We want an invisible cursor
- GOSUB DoCursor
- ELSE 'If program loaded for RAM residency...
- Ecode% = 0
- GOSUB BecomeResident 'Become memory-resident for the first time.
- END IF
-
-
- ' ============================================================================
- ' Main Program Section - This is the point where your program should be
- ' entered on each pop up.
- ' ----------------------------------------------------------------------------
-
- MainLoop:
- CALL MhMouseHide 'Hide the rodent
- GoSleep% = false
- terminate% = false
-
- ' ---- Store the screen as it existed before the calculator pops up
- WindSeg = VARSEG(Windmem%(zero))
- CALL MhMove(Monitor%, zero, screenArea, WindSeg, zero)
-
- ' ---- Save the panels to the right of the calculator panels.
- Dtaseg% = VARSEG(Area41%(zero))
- CALL MhSavePartScreen(ScrnCols%, 1, 41, ScrnRows%, ScrnCols%, Dtaseg%, zero)
- Dtaseg% = VARSEG(Area42%(zero))
- CALL MhSavePartScreen(ScrnCols%, 1, 42, ScrnRows%, ScrnCols%, Dtaseg%, zero)
- Dtaseg% = VARSEG(Area59%(zero))
- CALL MhSavePartScreen(ScrnCols%, 1, 59, ScrnRows%, ScrnCols%, Dtaseg%, zero)
-
- GOSUB FastKey 'Set the cursor speed
- GOSUB OpenCalc 'Open the calc like a wallet
-
- ShowIndicators 'Display inicators in Indicator window
- ScrLine CaptureLog0$, 4, 42, 10 'Display special info in indicator window
-
- ScrLine DispNumber$, 3, 12, 14 'Display the number in primary window
- ScrLine CalcDisp$, 9, 42, 14 'Display lookup info in lookup window
- ScrLine CaptureLog1$, 6, 42, 15 'Display history line number one
- ScrLine CaptureLog2$, 7, 42, 15 'Display history line number two
-
- ' ---- Establish the enter key as default starting point on first pass.
- IF CalcFunction = zero OR CalcFunction = 40 THEN
- prevHit = 28
- Col = 34
- FOR Row = 21 TO 23
- InverseVideo Row%, Col%, Monitor%
- NEXT
- Row = 23
- ELSE
- InverseVideo Row%, Col%, Monitor%
- END IF
-
- ' ---- All calculator operations are selected & processed from this loop
- DO
- MainMenu GoSleep%, terminate%, Row%, Col%, Monitor, CalcFunction, tableOn, hstOn%
- IF GoSleep% THEN
- CalcFunction = 10
- Row% = 9: Col% = 34
- EXIT DO
- ELSEIF terminate% THEN
- CalcFunction = 15
- Row% = 11: Col% = 34
- EXIT DO
- END IF
- ProcessTheHit Row%, Col%, GoSleep%, terminate%
- LOOP UNTIL GoSleep% OR terminate%
-
- ' ---- If we loaded without options then Sleep is the same as End
- IF LEN(cmmd$) = 0 AND GoSleep% = true THEN GoSleep% = false
-
- ' ---- If we were printing to lpt or disk then print the last number
- IF lptOn OR diskFile THEN ShowHist temp$
-
- ' ---- If we were outputting to a disk file then close the file.
- CALL MhCloseOFile(Ecode%)
-
- ' ---- Establish variables to redisplay when we pop back up
- CaptureLog0$ = SPACE$(29)
- CaptureLog1$ = CaptureLog0$
- CaptureLog2$ = CaptureLog0$
-
- ' ---- Fill these variables with info read from the monitor
- CALL MhRscr(CaptureLog0$, Page%, 4, 42, 29)
- CALL MhRscr(CaptureLog1$, Page%, 6, 42, 29)
- CALL MhRscr(CaptureLog2$, Page%, 7, 42, 29)
-
- IF GoSleep% THEN
- GOSUB GotoSleep
- GOTO MainLoop
- END IF
-
- GOTO ReleaseMem
-
-
- ' ============================================================================
- ' S U B R O U T I N E S
- ' ----------------------------------------------------------------------------
-
-
- ' ---- Set the cursor
- DoCursor:
- CALL MhLocate(Page%, CursorRow%, CursorCol%, Visible%, CursorStartScan%, CursorEndScan%)
- RETURN
-
- ' ---- Open the calculator
- OpenCalc:
- Operation% = 2' tells the routine to restore the window
- topRow% = 1
- BottomRow% = 24
- LeftCol% = 8
-
- FOR x = 1 TO 5
- IF x = 1 THEN
- RightCol% = 40
- ELSEIF x = 2 THEN
- RightCol% = 40
- ELSEIF x = 3 THEN
- RightCol% = 41
- ELSEIF x = 4 THEN
- RightCol% = 58
- ELSEIF x = 5 THEN
- RightCol% = 72
- END IF
-
- Buffer.number% = x
- Dtaseg% = VARSEG(CalcScrn%(zero))
- CALL Mhwind(Colr%, Dtaseg%, Operation%, Page%, topRow%, LeftCol%, BottomRow%, RightCol%, Buffer.number%, Box%, Ecode%)
- IF Ecode% GOTO Handler
-
- ' ---- Shadow the side of the calculator.
- IF x <> 2 THEN 'Prevent re-shadowing the first shadow created
- FOR ShadeRow% = 2 TO 24
- FOR Z = 1 TO 2
- IF x = 3 THEN Z = 2 'Prevent shadowing previous shadows!
- ShadeCol% = RightCol% + Z
- GOSUB CalcShade
- NEXT
- NEXT
- END IF
-
- ' ---- Shadow below the calculator.
- ShadeRow% = 25
- IF x <> 2 THEN 'Prevents re-shadowing the first shadow created
- IF x = 1 THEN
- Z = 10
- ELSEIF x = 3 THEN
- Z = 43
- ELSEIF x = 4 THEN
- Z = 44
- ELSEIF x = 5 THEN
- Z = 61
- END IF
- FOR ShadeCol% = Z TO RightCol% + 2
- GOSUB CalcShade
- NEXT
- END IF
-
- IF x = 1 THEN
- TickPause 45 'Approx 2 1/2 second delay (hold the copyright)
- ELSE
- TickPause 3 'Minor delay between animated frames
- END IF
- NEXT
-
- TickPause 5 'Slight pause after the calculator is opened
- RETURN
-
- ' ---- Close the calculator
- CloseCalc:
- FOR x = 4 TO 1 STEP -1 'First, restore original screens to right of calc
- IF x = 1 THEN
- RightCol% = 40
- ELSEIF x = 2 THEN
- RightCol% = 40
- Dtaseg% = VARSEG(Area41%(zero))
- CALL MhRestorePartScreen(ScrnCols%, 1, 41, ScrnRows%, ScrnCols%, Dtaseg%, zero)
- ELSEIF x = 3 THEN
- RightCol% = 41
- Dtaseg% = VARSEG(Area42%(zero))
- CALL MhRestorePartScreen(ScrnCols%, 1, 42, ScrnRows%, ScrnCols%, Dtaseg%, zero)
- ELSEIF x = 4 THEN
- RightCol% = 58
- Dtaseg% = VARSEG(Area59%(zero))
- CALL MhRestorePartScreen(ScrnCols%, 1, 59, ScrnRows%, ScrnCols%, Dtaseg%, zero)
- END IF
-
- ' ---- Re-display calc screens in reverse order
- Buffer.number% = x
- Dtaseg% = VARSEG(CalcScrn%(zero))
- CALL Mhwind(Colr%, Dtaseg%, Operation%, Page%, topRow%, LeftCol%, BottomRow%, RightCol%, Buffer.number%, Box%, Ecode%)
- IF Ecode% GOTO Handler
-
- ' ---- Reshadow the side of the calculator as it closes.
- IF x <> 1 THEN 'Prevent shadowing previous shadows!
- FOR ShadeRow% = 2 TO 25
- FOR Z = 1 TO 2
- ShadeCol% = RightCol% + Z
- GOSUB CalcShade
- NEXT
- NEXT
- END IF
-
- IF x = 1 THEN
- TickPause 30 'Delay the copyright screen about 1.67 seconds
- ELSE
- TickPause 3 'Slight pause between animated frames
- END IF
- NEXT
- RETURN
-
- ' ---- Get the color attributes from the monitor.
- GetChar:
- CALL MhGetChar(ShadeRow%, ShadeCol%, Char%, Attr%)
- RETURN
-
- ' ---- Restore the original screen that existed before the pop up
- RestoreDefaultScrn:
- WindSeg = VARSEG(Windmem%(zero))
- CALL MhMove(WindSeg, zero, screenArea, Monitor%, zero)
- RETURN
-
- ' ---- Change the color attributes on the monitor at specified locations.
- ScattAttrib:
- CALL MhScatt(Page%, ShadeRow%, ShadeCol%, Attr%, 1) ' Set new color Attr%
- RETURN
-
- ' ---- Set the cursor typmatic and delay rates.
- FastKey:
- CALL MhKeyboardSpeed(4, 1, 1, zero)
- RETURN
-
- ' ---- Return the cursor speed to it's original values.
- KeySpeedOff:
- CALL MhTurnOffKeyboardSpeed
- RETURN
-
- ' ---- Create a dual dimmensioned array that correlates row/col position
- ' with integers representing various calculator functions.
- BuildArray:
- '---- Establish function numbers for the left half of the calculator.
- choice% = 1
- FOR x = 7 TO 23
- IF x MOD 2 THEN
- check% = zero
- FOR Y = 10 TO 38
- check% = check% + 1
- IF check% < 6 THEN
- CalOps%(x, Y) = choice%
- END IF
- IF check% MOD 5 = zero THEN choice% = choice% + 1
- IF check% = 6 THEN check% = zero
- NEXT
- END IF
- NEXT
- '---- Correct the "=" key so that all its rows and cols = function 40.
- FOR x = 21 TO 23
- FOR Y = 34 TO 38
- CalOps%(x, Y) = 40
- NEXT
- NEXT
-
- '---- Establish function numbers for the right half of the calculator.
- choice% = 45
- FOR x = 12 TO 22
- IF x MOD 2 = zero THEN
- check% = zero
- FOR Y = 42 TO 70
- check% = check% + 1
- IF check% < 6 THEN
- CalOps%(x, Y) = choice%
-
- '---- Adjust for blank space before the "Deg" key
- IF check1% = false AND choice% = 60 THEN CalOps%(x, Y) = zero
-
- '---- Adjust for blank space after the "Grad" key
- IF check2% = false AND choice% = 63 THEN CalOps%(x, Y) = zero
- END IF
-
- '---- Adjust the "Deg" key to equal function 60.
- IF choice% = 60 AND check% = 5 AND check1% = false THEN
- check1% = true
- choice% = choice% - 1
- END IF
-
- '---- Adjust the "Float" key to equal function 63.
- IF choice% = 63 AND check% = 5 AND check2% = false THEN
- check2% = true
- choice% = choice% - 1
- END IF
-
- IF check% MOD 5 = zero THEN choice% = choice% + 1
- IF check% = 6 THEN check% = zero
- NEXT
- END IF
- NEXT
- ' ---- Zero out the temporary check integers.
- check% = zero: check1% = zero: check2% = zero
- RETURN
-
- ' ---- Set a shadow color attribute.
- CalcShade:
- GOSUB GetChar
- ' ---- The above call is EQV to Attr% = SCREEN(ShadeRow%, ShadeCol%, -1)
-
- Attr% = Attr% AND 15 ' Strip the background color from Attr%
- Attr% = Attr% - 8 ' Remove bright from the color
- IF Attr% < 1 THEN Attr% = 8 ' If color wasn't bright - make it grey
- GOSUB ScattAttrib
- RETURN
-
- GotoSleep:
- GOSUB CloseCalc 'Close the calculator
- GOSUB RestoreDefaultScrn 'Restore the original screen
-
- IF Mode% <> Kscan% THEN 'If we changed the video mode when
- CALL SrSetVideoMode(Kscan%) 'we popped up, change it back to
- END IF 'the original mode.
-
- Visible% = CursorOn% 'Reset cursor to original on/off mode
- GOSUB DoCursor 'Now, restore the original cursor
- GOSUB KeySpeedOff 'Reset the original typmatic speed
-
- IF LEN(stuff$) THEN StuffKey stuff$ 'Do we stuff the keyboard buffer?
-
- BecomeResident:
- HeapMem& = FRE("") 'Garbage collection
-
- CALL StayResident(Kscan%, Kshift%, Ecode%) 'Time to snooze
- CALL MhMouseReset(sn1%, sn2%)
-
- stuff$ = ""
- DosBusy% = zero
-
- IF Ecode% = 1 THEN 'Check for any errors
- DosBusy% = -1 'This flag can be checked by your prog-
- 'ram before using any DOS functions.
- ELSEIF Ecode% = 2 THEN 'Not enough memory to become resident.
- ScrLine SPACE$(screenArea / 2), 1, 1, 7
- ScrLine "Not Enough Memory. Program not loaded.", 2, 1, 7
- HiLowSounds
- END
-
- ELSEIF Ecode% <> zero THEN 'Other error occured
- ScrLine SPACE$(screenArea / 2), 1, 1, 7
- ScrLine ProgName$ + " Error" + STR$(Ecode%) + ProgTerminate$, 2, 1, 7
- HiLowSounds
- END
- END IF
-
- ' ---- Check the monitor type and video mode.
- GOSUB ScreenParams
-
- IF NOT (Kscan% = 2 OR Kscan% = 3 OR Kscan% = 7) THEN 'Check video mode.
- GOTO BecomeResident 'If it is too high, pop down.
-
- ' ---- Do we need to reset video mode?
- ELSEIF ((Kscan% = 7 AND Monitor = &HB000) OR ((Kscan% = 3 OR Kscan% = 2) AND Monitor = &HB800)) THEN
- Mode% = Kscan%
- GOTO GetCursorPosition 'No changes so don't reset video mode.
- ELSE 'Screen mode is different - so process it
- IF Monitor = &HB000 THEN
- Mode% = 7 'If color, set mode 7 (text mode).
- ELSE
- Mode% = 3 'If mono, set mode 3
- END IF
- END IF
-
- CALL SrSetVideoMode(Mode%) 'Reset video mode
-
- GetCursorPosition:
- ' ---- Get the state of the cursor.
- DEF SEG = zero
- CursorEndScan% = PEEK(&H460) 'Find end scan line
- CursorStartScan% = PEEK(&H461) AND &H1F 'Find start scan line
- IF NOT ((PEEK(&H461) AND 32) = 32) THEN 'Determine the state of the
- CursorOn% = 1 'cursor (on/off).
- ELSE
- CursorOn% = zero
- END IF
- DEF SEG
-
- Visible% = false 'Set cursor's visibility to off
- GOSUB DoCursor
- RETURN
-
- ScreenParams:
- CALL MhDisplay(Mode%, ScrnCols%, ScrnRows%, Mem%, DisplayType%)
- IF DisplayType% >= 128 THEN
- Monitor% = &HB800
- CalcScrn$ = "CALCSCRN.CLR"
- ELSE
- Monitor% = &HB000
- CalcScrn$ = "CALCSCRN.MON"
- END IF
- screenArea = ScrnCols% * ScrnRows% * 2
- RETURN
-
- ' ---- Come here when you want to "unload" your program from memory.
- ReleaseMem:
- IF ScreenError <> zero THEN END 'Error during program initialization
- GOSUB CloseCalc 'Close the calculator
- GOSUB KeySpeedOff 'Restore typmatic & delay rate
- GOSUB RestoreDefaultScrn 'Restore original screen
- Visible% = CursorOn% 'Reset cursor's on/off mode
- GOSUB DoCursor 'Restore original cursor
- IF LEN(stuff$) THEN StuffKey stuff$ 'Do we stuff keyboard buffer?
-
- IF cmmd$ = "" THEN END 'Not RAM resident so END
-
- CALL SrReleaseMem(RelEcode%) 'Release the memory
-
- IF RelEcode <> zero THEN
- ScrLine SPACE$(screenArea / 2), 1, 1, 7
- IF RelEcode = 7 THEN 'Must be over DOS to terminate
- ScrLine "Go to the DOS Command Line. Try again later.", 1, 1, 15
- HiLowSounds
- DO 'Clear the keyboard
- KeyResponce sn1%, sn2%, sn3%
- LOOP WHILE sn1% <> zero OR sn2% <> zero OR sn3% <> zero
- TickPause 36 'Two second pause
- stuff$ = ""
- GOSUB RestoreDefaultScrn
- ELSE 'Critical error encountered
- ScrLine MID$(goof$, 2) + STR$(RelEcode) + " releasing memory. You MUST Reboot!" + CHR$(13), 1, 1, 15
- HiLowSounds
- WHILE 1 = 1 'An infinite loop forces user to re-boot!
- WEND
- END IF
-
- ' ---- We tried to remove memory over another application. This is
- ' a no-no. So, we restore everything and return to main loop.
- Visible% = false 'Make the cursor invisible
- GOSUB DoCursor
- GOTO MainLoop 'Go back to the main logic code
- END IF
-
- END
-
- ' ---- Error catch during file handling while initializing program.
- Handler:
- ScrLine SPACE$(screenArea / 2), 1, 1, 7
- IF Ecode% = 258 THEN
- Lin$ = CalcScrn$ + " Not Found" + ProgTerminate$
- ELSE
- Lin$ = MID$(goof$, 2) + STR$(Ecode%) + ProgTerminate$
- END IF
- ScrLine Lin$, 1, 1, 7
- ScreenError = -1
- GOTO ReleaseMem
-
-
- ' ============================================================================
- ' Data Section - This is the point where the program should go
- ' to initialize the DATA statements.
- ' ----------------------------------------------------------------------------
-
- ' This program does not use DATA statements
-
- ' ============================================================================
- ' Subprograms And Functions
- ' ----------------------------------------------------------------------------
-
- ' There are numerous subprograms and functions in this and one other module.
-