home *** CD-ROM | disk | FTP | other *** search
/ Boston 2 / boston-2.iso / DOS / PROGRAM / BASIC / POWBASIC / LIBRARY3 / APLIB.ZIP / MENUS-U.BAS < prev    next >
BASIC Source File  |  1990-11-23  |  19KB  |  588 lines

  1.  
  2. '==============================================================================
  3. '                        ALL-PURPOSE LIBRARY
  4.  
  5. '                     THE NEW IMPROVED MENUS-U.BAS
  6. '==============================================================================
  7. '                                                               -- 2-18-90
  8. '                                                                  H Ballinger
  9.                             $COMPILE UNIT
  10.                             $ERROR ALL ON
  11.  
  12.  
  13.  DEFINT A-Z
  14.  
  15.  EXTERNAL RD$, VideoSeg&, ColorDisplay, NeedDCon
  16.  EXTERNAL BoxColor, FldColor, WinColor, MenuColor, BarColor
  17.  EXTERNAL PressAKeyBeep$, OopsBeep$, TinyBeep$
  18.  EXTERNAL ButtonsActive, TimeOut
  19.  EXTERNAL BXScreenSaved, PMScreenSaved
  20.  EXTERNAL MenuHelpLine$()
  21.  EXTERNAL UseRArrow, UseLArrow, UsePgUp, UsePgDn, PullDown
  22.  
  23.  DECLARE SUB Marker (string)
  24.  
  25.  %False = 0
  26.  %True = NOT %False
  27.  %ButtonsDefined = 0
  28.  
  29.  %ResetRodent = 0 '        mouse routine and humor (??) courtesy of Barry Erick
  30.  %ReadRodent = 3
  31.  %LeftButton = 1
  32.  %RightButton = 2
  33.  %Wht = 15
  34.  %MouseVertSensit = 1 '                   controls mouse sensitivity in POPMENU
  35.  %MouseHorizSensit = 10 '                controls mouse sensitivity in POPMENU
  36.  %MouseIcon = 15 '              ... a little sun or bug character
  37.  
  38.  %MaxMenuWidth = 40
  39.  
  40. '  MENU RETURN CODES (KEY PRESSED.)
  41.       %CR = 0:    %Esc = &H20:          %F1 = &H100:           %F2 = &H200
  42.             %PgUp = &H400:              %PgDn = &H600
  43.             %RArrow = &H800:            %LArrow = &HA00
  44.  
  45.  
  46.  
  47.  DECLARE SUB Mouse (integer, integer, integer, integer)
  48.  
  49.  
  50. ' ----------------------------------------------------------------------------
  51.  
  52. SUB TOPMENU (Lines% ,Choice, TLine$) PUBLIC
  53.  
  54.  LOCAL I$(), K$(), Choices%, D$, LEach, L, SpacesLeftOver, I%, B$, Att,_
  55.   Choice$, Click, Ln, Col, RefTime&
  56.  
  57.  STATIC mcsrX, mcsrY
  58.  IF %ButtonsDefined THEN ButtonActive = %False
  59.  TLine$ = ""
  60.  
  61. TReadlines:
  62.  DIM I$(6): DIM K$(6)
  63.  Choices% = 0
  64.  
  65.  READ D$
  66.  
  67.  DO WHILE D$ <> "END"
  68.    INCR Choices%
  69.    I$(Choices%) = D$
  70.    K$(Choices%) = LEFT$(D$,1)
  71.    READ D$
  72.  LOOP
  73.  
  74.  
  75.  LOCATE ,,0
  76.  
  77.  
  78. TSetVars:
  79.  IF Choice = 0 THEN Choice = 1
  80.  LEach = 80\Choices%
  81.  SpacesLeftOver = 80 - Choices% * LEach
  82.  
  83.  FOR I% = 1 TO Choices% '                      create menu elements
  84.   B$ = I$(I%)
  85.   L = ((LEach - LEN(B$))/2) + 1: IF L<2 THEN L=2 '               fixed 12-88
  86.   I$(I%) = SPACE$(LEach)
  87.   MID$ (I$(I%), L) = B$
  88.   IF SpacesLeftOver THEN I$(I%) = I$(I%)+" ": DECR SpacesLeftOver
  89.  NEXT I%
  90. '                                      making their total length = 80 chrs
  91.  DEF SEG = VideoSeg&
  92.  BLAtt = PEEK (3841)
  93.  DEF SEG
  94.  
  95.  COLOR MenuColor MOD 16, MenuColor \ 16
  96.  LOCATE 25,1: PRINT "CHOOSE MAIN PROGRAM FUNCTION FROM TOP ROW.";
  97.                PRINT " USE ARROWS TO SELECT THEN PRESS [CR]";
  98.  DEF SEG = VideoSeg&
  99.  POKE 3998, ASC("."): POKE 3999,PEEK (3997)
  100.  DEF SEG '                                  menu borders & help line printed
  101.  
  102.  LOCATE 1,1
  103.  IF Lines% > 2 THEN PRINT STRING$ (80, 205)
  104.  IF TLine$ <> "" THEN LOCATE 1, (40 - LEN(TLine$)\2): PRINT TLine$;
  105. TDisp:
  106.  Att = 16
  107.  GOSUB TPrint '                                     print menu elements
  108.  COLOR MenuColor MOD 16, MenuColor \ 16
  109.  IF Lines% > 1 THEN LOCATE 3,1:PRINT STRING$ (80, 205)
  110.  
  111. TGetChoice:
  112.  IF NeedDCon THEN
  113.    Cheese = 0
  114.    Choice$ = ""
  115.    DEF SEG = VideoSeg&
  116.    StoredChr = PEEK (Addr): StoredAttr = PEEK (Addr+1)
  117.    DO
  118.      CALL Mouse (%ReadRodent, Click, mcsrX, mcsrY)
  119.  
  120.      IF Addr <> mcsrX/4 + 160*INT(mcsrY/8) THEN
  121.        POKE Addr, StoredChr
  122.        POKE Addr+1, StoredAttr
  123.        Addr = mcsrX/4 + 160*INT(mcsrY/8)
  124.        StoredChr = PEEK (Addr)
  125.        StoredAttr = PEEK (Addr+1)
  126.        POKE Addr, %MouseIcon '                         move the mouse cursor if nec.
  127.        POKE Addr+1, %Wht OR PEEK (Addr+1)
  128.      END IF
  129.  
  130.      IF (Click = %LeftButton) AND (mcsrY < 60) THEN '   you clicked on top bar:
  131.        Choice = INT (mcsrX * Choices% / 640) + 1  '       so move cursor ...
  132.        Att = 16
  133.        GOSUB TPrint '                                  &  reprint menu elements
  134.        IF mcsrY > 0 AND mcsrY < 30 THEN
  135.          Choice$ = CHR$(13)
  136.          POKE Addr, StoredChr
  137.          POKE Addr+1, StoredAttr
  138.          EXIT LOOP
  139.        END IF
  140.      END IF
  141.  
  142.    IF ButtonsDefined THEN                        ' ---------------------------|
  143.      IF Click AND mcsrY > 112 THEN
  144.        Ln = mcsrY / 8 + 1 '                    8 mickeys per line
  145.        Col = mcsrX / 8 + 1 '                     8 mickeys per column
  146.        IF Ln > 18 AND Ln < 25 THEN
  147.          IF Col > 8 AND Col < 23 THEN ButtonActive = %DirButton: EXIT LOOP
  148.          IF Col > 30 AND Col < 44 THEN ButtonActive = %TreeButton: EXIT LOOP
  149.        END IF
  150.        IF (Ln > 14 AND Ln < 18) AND (Col > 68 AND Col < 75) THEN _
  151.                                          ButtonActive = %HelpButton: EXIT LOOP
  152.      END IF
  153.  
  154.    END IF                                 ' ----------------------------------|
  155.  
  156.      IF TimeOut AND (TIMER > RefTime& + TimeOut) THEN
  157.        TimeUp = %True
  158.        EXIT LOOP
  159.      END IF
  160.  
  161.    LOOP UNTIL INSTAT
  162. '   LPRINT "ButtonActive ="; ButtonActive
  163.    IF Choice$ = "" THEN Choice$ = INKEY$
  164.    DEF SEG
  165.  
  166.  ELSE
  167.  
  168.    DO
  169.      IF TimeOut AND (TIMER > RefTime& + TimeOut) THEN
  170.        TimeUp = %True
  171.        EXIT LOOP
  172.      END IF
  173.    LOOP UNTIL INSTAT
  174.  
  175. '                                                         ****************
  176.    Choice$ = INKEY$ '                                   ** GET KEYSTROKE **
  177. '                                                         ****************
  178.  END IF
  179.  
  180.  IF TimeUp OR ButtonActive THEN BEEP:BEEP: Choice = 1 : GOTO TDone
  181.  
  182.  IF LEN(Choice$) > 1 THEN '                        you pressed an arrow key ...
  183.    SELECT CASE RIGHT$(Choice$,1)
  184.      CASE CHR$(&H4D)
  185.        GOSUB TRightArrow
  186.      CASE CHR$(&H4B)
  187.        GOSUB TLeftArrow
  188.      CASE CHR$(&H50)
  189.        Choice$ = CHR$(13)
  190.      CASE CHR$(59)
  191.        TLine$ = "HELP!"
  192.        GOTO TDone
  193.      CASE ELSE
  194.        GOTO TError
  195.    END SELECT
  196.  END IF
  197.  
  198.  IF Choice$ = CHR$(13) THEN Choice$ = K$(Choice): GOTO TDone
  199.  IF Choice$ = CHR$(27) THEN Choice = Choices%: GOTO TDone
  200.  Choice$ = UCASE$(Choice$)
  201.  FOR I = 1 TO Choices%
  202.    IF Choice$ = K$(I) THEN Choice = I:GOTO TDone
  203.  NEXT
  204.  GOTO TError
  205.  
  206. TError:
  207.  
  208.  PLAY OopsBeep$
  209.  GOTO TGetChoice
  210.  
  211. TLeftArrow:
  212.    DECR Choice
  213.    IF Choice < 1 THEN Choice = Choices%
  214.    RETURN TDisp
  215.  
  216. TRightArrow:
  217.    INCR Choice
  218.    IF Choice > Choices% THEN Choice = 1
  219.    RETURN TDisp
  220.  
  221. TDone:
  222.   Att = 0: GOSUB TPrint
  223.   IF TLine$ <> "HELP!" THEN TLine$ = RTRIM$ (LTRIM$ (I$ (Choice)))
  224.   COLOR BLAtt MOD 16, BLAtt \ 16
  225.   LOCATE 25, 1, 1
  226.   PRINT SPACE$ (80);
  227.   EXIT SUB
  228.  
  229. TPrint:
  230.  LOCATE Lines%-1,1
  231. '                          IF Choice < 1 OR Choice > Choices% THEN Choice = 1
  232.  FOR I% = 1 TO Choices%
  233.    IF I% = Choice THEN
  234.      COLOR Att + (BarColor MOD 16), BarColor \ 16
  235.    ELSE
  236.      COLOR MenuColor MOD 16, MenuColor \ 16
  237.    END IF
  238.    PRINT I$(I%);
  239.  NEXT
  240.  RETURN
  241.  
  242.  END SUB                                                    REM TOPMENU
  243.  
  244. ' ==============================================================================
  245.  
  246. SUB POPMENU (TopKey$,MenuRight,MenuDown,Choice,MLine$,MCode$) PUBLIC
  247. '   ====
  248.  
  249.  LOCAL Choices%, D$,A$, Maxx, Title$, MKeyPressed$, PopRead$ ()
  250.  DIM DYNAMIC PopRead$ (24)
  251.  
  252.  
  253. MReadlines:
  254.  
  255.  Choices% = 0: A$ = ""
  256.  
  257.  READ D$ '                   read 2 $'s- the menu line & the assoc. memo
  258.  
  259.  DO WHILE D$ <> "END" AND A$ <> "END" '                     (from data list)
  260.    READ A$
  261.    IF Choices% < 24 THEN INCR Choices% '                          count 1 item
  262.    PopRead$(Choices%) = D$
  263.    IF TopKey$ <> "" THEN PopRead$(Choices%) = "  " + PopRead$(Choices%)
  264.    MenuHelpLine$(Choices%) = A$                          '     plug arrays --
  265.    READ D$ '                                                 ... longest $ is
  266.  LOOP
  267.  PopRead$ (Choices% + 1) = "END"
  268.  
  269.  Title$ = MLine$
  270.  
  271.        CALL SUPERMENU (PopRead$ (), MenuRight, MenuDown, Choice, Title$, Ky%)
  272.  
  273.  MCode$ = MenuHelpLine$(Choice)
  274.  MLine$ = PopRead$ (Choice)
  275.  ERASE PopRead$
  276.  
  277. END SUB                                                           REM POPMENU
  278. '______________________________________________________________________________
  279.  
  280. SUB SUPERMENU (MenuData$ (), MenuRight, MenuDown, Choice, Title$, Ky%) PUBLIC
  281. '   ====
  282. '
  283. '                               ===================
  284. '
  285. '     BRIEF SYNTAX:   MenuData$ () ARRAY holds items in menu
  286. '
  287. '          ferexample, MenuData$ (1) = "L LOAD" (pressing L will select)
  288. '                or ... MenuData$ (1) = "  LOAD" (pressing 1 will select)
  289. '
  290. '           After all menu lines are defined, the next array item must be "END"
  291. '
  292. '                     MenuRight may be >0 for right of center, <0 for left.
  293. '                     MenuDown = 0 places menu at screen top; >24 centers it.
  294. '
  295. '                     Choice is usually set as 1 before calling menu
  296. '
  297. '                     Title$ is just a menu title
  298. '
  299. '
  300. '
  301. '*** AFTER SUPERMENU CALL: Choice will hold the choice # (according to array passed)
  302. '
  303. '                     Ky% will encode the key used to exit the menu process --
  304. '                       %CR, %Esc, %PgUp, %PgDn, %RArrow, %LArrow, %F1, %F2
  305. '
  306. '        (PgUp key will only function if the global var UsePgUp = %Yes, and
  307. '         similarly for the others. If there is another page, cursoring or
  308. '         mousing past the bottom of the displayed page will simulate
  309. '         pressing PgDn, etc. All these globals are reset to %False after exit,
  310. '         but UseF1 isn't.
  311. '
  312.  
  313.  
  314.  
  315.  LOCAL Choices%, D$, A$, K$(), Longest, HelpLines, TopKey
  316.  LOCAL Wid, Height, K$, CornerLin, CornerCol, N, C
  317.  DIM K$ (24)
  318.  Ky% = 0
  319.  
  320.  
  321. '      ======= START; GET WIDTH OF ITEMS AND HOW MANY ===============
  322.  
  323.  LOCATE ,,0
  324.  ArrayNum = 1
  325.  DO UNTIL UCASE$ (RTRIM$ (LTRIM$ (MenuData$(ArrayNum) ))) =  "END"
  326. ''''''''''                      CALL Marker ("ArrayNum "+STR$(ArrayNum))#######
  327.    INCR Choices%
  328.    IF LEN (RTRIM$ (MenuData$(ArrayNum))) > Longest THEN_
  329.                       Longest = LEN (RTRIM$ (MenuData$(ArrayNum)))
  330.      'keep track of how long the items are ...
  331.    K$ (ArrayNum) = LEFT$ (MenuData$ (ArrayNum), 1)
  332.    IF MenuHelpLine$ (ArrayNum) <> "" THEN INCR HelpLines
  333.    INCR ArrayNum
  334.  LOOP
  335.  DECR Longest, 2  '          clip off the 2 chrs which are not part of the item
  336.  
  337. '      ==================== DO CALCULATIONS FOR MENU ===========================
  338. MSetVars:
  339.  
  340.  VCentered = (MenuDown > 23) '                           trap hi MenuDown value
  341.  Wid = Longest + 6  '                                       compute box size --
  342.  Height = Choices%+2
  343.  MenuDown = MAX% (0, MenuDown)
  344.  MenuDown = MIN% ((23-Choices%), MenuDown)
  345.  MenuRight = MIN% ((40 - Wid\2), MenuRight)
  346.  MenuRight = MAX% (-39, MenuRight)
  347.  CornerCol = INT((80-Wid)/2 + MenuRight)'            & the top left corner --
  348.  CornerCol = MAX% (1, CornerCol)
  349.  CornerLin = INT(1 + MenuDown)
  350.  CornerLin = MAX% (1, CornerLin)
  351.  IF VCentered THEN CornerLin = (24-Height)/2 + 1 '  trap hi MenuDown value
  352.  IF TopKey$ <> "" THEN TopKey = ASC(TopKey$)'         (means center vertically)
  353.  BAR$ = "\"+SPACE$(Wid-8)+"\"
  354.  Choice = MAX% (1, Choice)
  355.  Choice = MIN% (Choices% , Choice)
  356.  IF LEFT$ (MenuData$ (1), 1) = " " THEN
  357.    IF Choices% > 9 THEN TopKey = ASCII ("A") ELSE TopKey = ASCII ("1")
  358.  END IF
  359.  
  360. MPrint:
  361.  
  362.  L0 = CSRLIN: C0 = POS
  363.  COLOR MenuColor MOD 16, MenuColor \ 16
  364.  
  365. '      =================== BEGIN PRINTING MENU =====================
  366.  
  367.  LOCATE CornerLin,CornerCol: PRINT CHR$(201); STRING$((Wid-1),205); CHR$(187)
  368.  IF Title$ <> "" THEN LOCATE CornerLin,CornerCol+2: PRINT " ";Title$;" "
  369. '                                                top of menu frame is complete
  370.  
  371.  '                                                             print menu lines
  372.  FOR N = 1 TO Choices%
  373.    IF TopKey > 0 THEN K$ (N) = CHR$(TopKey-1+N)
  374.    LOCATE N+CornerLin, CornerCol
  375.    PRINT CHR$(186); " "; K$(N); " - ";
  376.    PRINT USING BAR$; MID$(MenuData$(N),3); : PRINT CHR$(186);
  377.  NEXT
  378.  '                                                             print bottom bar
  379.  LOCATE N+CornerLin,CornerCol:PRINT CHR$(200); STRING$((Wid-1),205); CHR$(188);
  380.  
  381.  IF PullDown THEN '                                  hold here if clicking ...
  382.    Click = %False
  383.    DO
  384.      IF NeedDCon THEN CALL Mouse (%ReadRodent, Click, X, Y)
  385.      IF Y0 = 0 THEN Y0 = Y
  386.      IF Click THEN
  387.        IF Y - Y0 > %MouseVertSensit THEN
  388.          MouseNotMoved = %False '                     unless mouse moved down.
  389.          EXIT LOOP
  390.        ELSE
  391.          MouseNotMoved = %True
  392.        END IF
  393.      END IF
  394.    LOOP WHILE Click
  395.    IF MouseNotMoved THEN Choice = 0: GOTO ExitMenu
  396.  END IF
  397.  
  398.  GOSUB DrawHighlightedBar
  399.  
  400. MGetChoice:
  401.  DO '                                         ********************************
  402.    Click = %False '                          ** GET KEYSTROKE OR MOUSE INPUT **
  403.    WasClick = %False '                        ********************************
  404.    Choice$ = ""
  405.    DO
  406.      IF NeedDCon THEN
  407.        CALL Mouse (%ReadRodent, Click, X, Y)
  408.        IF Click THEN
  409.          IF Click >= %RightButton THEN
  410.            Choice$ = CHR$(27)
  411.            EXIT LOOP
  412.          END IF
  413.          IF WasClick THEN
  414.            IF X - X0 > %MouseHorizSensit THEN
  415.              Choice$ = CHR$(0) + CHR$ (&H4D)
  416.            ELSEIF X0 - X > %MouseHorizSensit THEN
  417.              Choice$ = CHR$(0) + CHR$ (&H4B)
  418.            ELSEIF Y - Y0 > %MouseVertSensit THEN
  419.              Choice$ = CHR$(0) + CHR$ (&H50)
  420.            ELSEIF Y0 - Y > %MouseVertSensit THEN
  421.              Choice$ = CHR$(0) + CHR$ (&H48)
  422.            END IF
  423.          END IF
  424.          X0 = X: Y0 = Y: WasClick = Click
  425.        ELSE
  426.          IF WasClick THEN
  427.            Choice$ = CHR$(13)
  428.            FOR I = 1 TO 5 '                            this builds in a slight
  429.              DELAY .05 '                               delay (1/4 sec.) after
  430.              CALL Mouse (%ReadRodent, Click, X, Y) '   mouse button is released
  431.              IF Click >= %RightButton THEN '           during which the right
  432.                Choice$ = CHR$(27) '                    (cancel) button can be
  433.                EXIT FOR '                              pressed if you change
  434.              END IF '                                  your mind.
  435.            NEXT
  436.          ELSE
  437.            Choice$ = UCASE$(INKEY$)
  438.          END IF
  439.        END IF
  440.      ELSE
  441.        Choice$ = UCASE$(INKEY$)
  442.      END IF
  443.      OldChoice = Choice
  444.    LOOP UNTIL Choice$ <> ""
  445.  
  446.  '                  ======================== CHOICE HAS BEEN MADE ...
  447.  
  448.    SELECT CASE Choice$
  449.          CASE CHR$ (0 ) + CHR$(&H48 )
  450.            GOSUB MUpArrow
  451.          CASE CHR$ (0 ) + CHR$(&H50 )
  452.            GOSUB MDownArrow
  453.          CASE CHR$ (0 ) + CHR$(&H4B )
  454.            IF UseLArrow THEN GOSUB MLArrow
  455.          CASE CHR$ (0 ) + CHR$(&H4D )
  456.            IF UseRArrow THEN GOSUB MRArrow
  457.          CASE CHR$ (0 ) + CHR$(&H3B )
  458.            GOSUB MF1Key
  459. '    deleted       CASE CHR$ (0 ) + CHR$(&H3C )
  460. '    deleted         GOSUB MF2Key
  461.          CASE CHR$ (0 ) + CHR$(&H49 )
  462.            IF UsePgUp THEN GOSUB MPgUpKey
  463.          CASE CHR$ (0 ) + CHR$(&H51 )
  464.            IF UsePgDn THEN GOSUB MPgDnKey
  465.          CASE CHR$(13)
  466.             Choice$ = K$(Choice) '                    you pressed [CR]
  467.  
  468.          CASE CHR$(27)'     you pressed [ESC]. Sets return var as 0 and exits.
  469. '                           First erase the highlighted bar by rewriting it ...
  470.             COLOR MenuColor MOD 16, MenuColor \ 16
  471.             LOCATE (Choice+CornerLin),(CornerCol+1)
  472.             PRINT " ";K$(Choice);" - ";
  473.             PRINT USING BAR$;MID$(MenuData$(Choice),3);
  474.             Choice = 0
  475.             Ky% = %Esc
  476.             EXIT LOOP ' --------------------------------------------------------
  477.    END SELECT
  478.  
  479. '                                                              & chose Choice$
  480. '                Your entry is checked vs. list of K$'s,  If it's valid
  481. '                                             then Choice is set appropriately.
  482.      FOR I = 1 TO Choices%
  483.        IF Choice$ = K$(I) THEN Choice = I: EXIT LOOP
  484.      NEXT
  485.  
  486.  LOOP
  487.  
  488. ExitMenu:
  489.  IF Choice > 0 THEN GOSUB MoveBar
  490.  MenuDown = 0: MenuRight = 0
  491.  UsePgUp = 0: UsePgDn = 0: UseRArrow = 0: UseLArrow = 0: PullDown = 0
  492.  FOR N = 1 TO Choices%: MenuHelpLine$(N) = "": NEXT
  493.  LOCATE L0,C0,1
  494.  EXIT SUB
  495.  
  496.  
  497.  
  498. MoveBar:
  499.    COLOR MenuColor MOD 16, MenuColor \ 16 '                 NOTE: THIS IS ONE
  500.    LOCATE (OldChoice+CornerLin),(CornerCol+1) '             OF THOSE DREADED
  501.    PRINT " ";K$(OldChoice);" - "; '                         TWO-HEADED SUB-
  502.    PRINT USING BAR$;MID$(MenuData$(OldChoice),3); '         ROUTINES. MoveBar
  503. '                                                           RUNS RIGHT INTO
  504. DrawHighlightedBar: '                                       DrawHighLightedBar!
  505.    COLOR BarColor MOD 16, BarColor \ 16 '                   (works just Fine!)
  506.    LOCATE (Choice + CornerLin),(CornerCol+1)
  507.    PRINT " ";K$(Choice);" - ";
  508.    PRINT USING BAR$;MID$(MenuData$(Choice),3);
  509.                                            ''  print bottom line on screen
  510.    IF HelpLines THEN GOSUB MClearLine
  511.    IF LEN(MenuHelpLine$(Choice)) > 9 THEN
  512.        MenuHelpLine$(Choice) = Left$(MenuHelpLine$(Choice), 78)  ' trap long ln
  513.        COLOR MenuColor MOD 16, BarColor \ 16
  514.        LOCATE 25, (41-LEN(MenuHelpLine$(Choice))/2)
  515.        PRINT MenuHelpLine$(Choice);
  516.    END IF
  517.    RETURN
  518.  
  519. MUpArrow:
  520.    DECR Choice
  521.    IF Choice < 1 THEN
  522.      IF PullDown THEN
  523.         '                                   an up-arrow when the bar is at
  524.        Choice = 0 '                           the top will clear the menu
  525.        RETURN ExitMenu
  526.      ELSEIF UsePgUp THEN
  527.        Ky% = %PgUp
  528.        RETURN ExitMenu
  529.      ELSE
  530.        Choice = Choices%
  531.      END IF
  532.    END IF
  533.    GOSUB MoveBar: RETURN
  534.  
  535. MDownArrow:
  536.    INCR Choice
  537.    IF Choice > Choices% THEN
  538.      IF PullDown THEN
  539.        DECR Choice
  540.      ELSEIF UsePgDn THEN
  541. '                             erase the highlighted bar by rewriting it ...
  542.        COLOR MenuColor MOD 16, MenuColor \ 16
  543.        DECR Choice
  544.        LOCATE (Choice + CornerLin), (CornerCol+1)
  545.        PRINT " "; K$ (Choice); " - ";
  546.        PRINT USING BAR$; MID$ (MenuData$ (Choice), 3);
  547.        Choice = 0
  548.        Ky% = %PgDn
  549.        RETURN ExitMenu
  550.      ELSE
  551.        Choice = 1
  552.      END IF
  553. '                               IF PullDown THEN DECR Choice ELSE Choice = 1
  554.    END IF
  555.    GOSUB MoveBar: RETURN
  556.  
  557. MF1Key:
  558.    Ky% = %F1
  559.    Choice = 0 '                  just as if ESC had been pressed
  560.    RETURN ExitMenu
  561.  
  562. MF2Key:
  563.    Ky% = %F2
  564.    RETURN ExitMenu
  565.  
  566. MPgUpKey:
  567.    Ky% = %PgUp
  568.    RETURN ExitMenu
  569.  
  570. MPgDnKey:
  571.    Ky% = %PgDn
  572.    RETURN ExitMenu
  573.  
  574. MRArrow:
  575.    Ky% = %RArrow
  576.    RETURN ExitMenu
  577.  
  578. MLArrow:
  579.    Ky% = %LArrow
  580.    RETURN ExitMenu
  581.  
  582. MClearLine:
  583.    LOCATE 25,1
  584.    PRINT STRING$ (80," ");
  585.    RETURN
  586.  
  587.  END SUB                                                         REM SUPERMENU
  588.