Below is the menu processing code used in ScreenIO.
fnDisplayWindowsMenu and fnClearWindowsMenu are used to place the menu on the screen. fnDefineWindowsMenu is called by fnDisplayWindowsMenu, and that function contains the definition of what goes on the menu.
fnProcessWindowsMenu is called after the main input fields statements like follows:
Afterwords MenuResult is queried to see if we need to exit or do anything else major with the flow of the program. Minor things are handled directly in fnProcessWindowsMenu.
The key thing to notice is that the menu definition is done with old fasioned READ and DATA statements, and that EOF is tested to see when we're done. That way I can add new items to the menu by simply changing the DATA statements and nothing else. Your CSV solution accomplishes the same result.
Next thing to notice is that the second menu parameter is used to give an internal "Name" to the menu item. This name is tested in fnProcessWindowsMenu, using lexi's Select Case statement. (The same thing can be accomplished in BR using if.. then.. else if.. I just think Select Case is easier to read and work with.
This Select Case statement checks which menu item was selected and reacts accordingly.. either running that menu items code right there, or else returning a flag so the calling code can handle it.
Finally, regarding CX menu items.. any menu items that are CX menu items automatically are given a BR environment variable that matches the internal "name" for the menu item. This environment variable is set to true when its checked and false when its unchecked.
In fnProcessWindowsMenu if we get to any menu items that we don't have special code for, it then checks to see if its a "C" menu item, and if it is, it updates the environment variable to match the new checked status of the menu.
The end result of all this is that if I need to add something new to the ScreenIO menu, if its a regular item, all I do is add the data statement and add some code to fnProcessWindowsMenu to the SELECT CASE statement to "do" the new menu item. If I want to add a new Checkbox menu item, all I do is add it to the list, and make my code that needs to see if its checked test the environment variable.
It may be a little complicated to understand the setup initially. But it makes it much easier to make changes to it in the future (and I've had to make many many changes to this part of the program.)
Code: Select all
def Fndisplaywindowsmenu(;___,Index)
dim M$(1)*30, Pgm$(1), Status$(1)
let Fndefinewindowsmenu(Mat M$,Mat Pgm$, Mat Status$)
!
display Menu: Mat M$, Mat Pgm$, Mat Status$
fnend
!
def Fnclearwindowsmenu
dim Mclear$(1), Pgmclear$(1), Statusclear$(1)
!
mat Mclear$(0) : mat Pgmclear$(0) : mat Statusclear$(0)
!
display Menu: Mat Mclear$, Mat Pgmclear$, Mat Statusclear$
fnend
def Fndefinewindowsmenu(Mat M$, Mat Pgm$, Mat Status$;___,Index)
!
restore DEFINEWINDOWSMENU
data "&File","",""
data " &New","new","E"
data " &Load","load","E"
data " &Save and Compile","save","E"
data " &Compile","recompileone","E"
data " -","",""
data " E&xport Screen","export","E"
data " &Import Screen","import","E"
data " -","",""
data " &Purge ScreenFlds File","purge","E"
data " Recompile &All Screens","recompile","E"
data " -","",""
data " &Quit","quit","E"
data "&Options","",""
data " Click To &Move","clickmove","ECX"
data " Preview &Listviews","poplist","ECX"
data " Real-Time &Filters","filter","EC"
data "&Tools","",""
data " Power &Search","search","E"
data " &Code Explorer","codeexplore","E"
data "&Add Control","",""
data " Add &Field","add field","E"
data " Add E&xit Buttons","exit buttons","E"
data " -","",""
data " Add &TextBox","add textbox","E"
data " Add &Caption","add caption","E"
data " Add C&heckBox","add checkbox","E"
data " Add &Listview","add listview","E"
data " Add &SearchBox","add search box","E"
data " Add &Button","add button","E"
data " Add &Picture","add picture","E"
data " -","",""
data " S&kip a Space","skip a space","E"
data "&Screen","",""
data " &Adjust Screen Size","resize screen","E"
data " &Move Controls","movemode","E"
data " Visit &Checklist","debuglist","E"
data " -","",""
data " Set &FG Color","setfgcolor","E"
data " Set &BG Color","setbgcolor","E"
data " Select File &Layout","selectlayout","E"
data " Set &Events","events","E"
data " Set &Tab Order","taborder","E"
data " -","",""
data " Configure &Debug","debug","E"
data " -","",""
data " Test &Screen","test","E"
data "&Help","",""
data " &Documentation","help","E"
data " -","",""
data " &About","about","E"
!
mat M$(0) : mat Pgm$(0) : mat Status$(0)
READNEXTMENU: ! Read The Next Menu Option Here
mat M$(Udim(Mat M$)+1) : mat Pgm$(Udim(Mat M$)) : mat Status$(Udim(Mat M$))
read M$(Udim(Mat M$)), Pgm$(Udim(Mat M$)), Status$(Udim(Mat M$)) eof DONEREADMENU
goto READNEXTMENU
DONEREADMENU: ! Finished Reading The Menu
! . ! Apply Checkmark Environment Variables
for Index=1 to Udim(Mat Pgm$)
if Pos(Uprc$(Status$(Index)),"C") then
if Pos(Uprc$(Trim$(Env$(Pgm$(Index)))),"Y") then
if ~(Pos(Uprc$(Status$(Index)),"X")) then
let Status$(Index)=Status$(Index)&"X"
end if
else if Pos(Uprc$(Trim$(Env$(Pgm$(Index)))),"N") then
let Status$(Index)=Srep$(Uprc$(Status$(Index)),"X","")
else
if Pos(Uprc$(Status$(Index)),"X") then
let Setenv(Pgm$(Index),"Y")
else
let Setenv(Pgm$(Index),"N")
end if
end if
end if
next Index
fnend
!
PROCESSWINDOWSMENU: ! Process A Command From The Windows Menu
def Fnprocesswindowsmenu(Mat Screenio$, Mat Screenio,[[Screencontrols]];___,Screen$)
!
dim Menunew, Menuload, Menusave, Menuquit, Menuabout, Menuhelp, Menuevents, Menutaborder
dim Menuexport, Menuimport, Menurecompile, Menutest, Menurecompileone, Menupurge, Menudebug
dim Menufgcolor, Menubgcolor, Menuselectlayout, Menumovement, Menudebuglist, Menufieldslist, Menuaddcontrol
!
let Menunew=1 : let Menuload=2 : let Menusave=3 : let Menuquit=4
let Menuabout=5 : let Menuhelp=6 : let Menuevents=7 : let Menutaborder=8
let Menuexport=9 : let Menuimport=10 : let Menurecompile=11 : let Menutest=12
let Menurecompileone=13 : let Menupurge=14 : let Menudebug=15
let Menufgcolor=16 : let Menubgcolor=17 : let Menuselectlayout=18 : let Menumovement=19
let Menudebuglist=20 : let Menufieldslist=21 : let Menuaddcontrol=22
!
#Select# Lwrc$(Menu$) #Case# "new"
if Fnoktoproceed(Mat Screenio$,Mat Screenio,[[Screencontrols]]) then
let Fnreadscreen("",Mat Screenio$,Mat Screenio,[[Screencontrols]])
let Fnprocesswindowsmenu=Menunew
end if
#Case# "load"
if Fnoktoproceed(Mat Screenio$,Mat Screenio,[[Screencontrols]]) then
let Screen$=Fnselectscreen$
if Trim$(Screen$)<>"" then
if Fnreadscreen(Screen$,Mat Screenio$,Mat Screenio,[[Screencontrols]]) then
let Fnprocesswindowsmenu=Menuload
else
let Msgbox("Error Reading Screen - Screen not found","Error","OK","ERR")
end if
end if
end if
#Case# "recompileone"
if Fncompilehelperlibrary(Mat Screenio$,Mat Screenio,[[Screencontrols]]) then
let Fnprocesswindowsmenu=Menurecompileone
end if
#Case# "save"
if Fnwritescreen(Mat Screenio$,Mat Screenio,[[Screencontrols]]) then
let Fnprocesswindowsmenu=Menusave
end if
#Case# "quit"
if Fnoktoproceed(Mat Screenio$,Mat Screenio,[[Screencontrols]]) then
let Fnprocesswindowsmenu=Menuquit
end if
#Case# "export"
if Fnexportscreen(Mat Screenio$,Mat Screenio,[[Screencontrols]]) then
let Fnprocesswindowsmenu=Menuexport
end if
!
#Case# "import"
if Fnoktoproceed(Mat Screenio$,Mat Screenio,[[Screencontrols]]) then
if Fnimportscreen(Mat Screenio$,Mat Screenio,[[Screencontrols]]) then
let Fnprocesswindowsmenu=Menuimport
end if
end if
!
#Case# "recompile"
if Fnoktoproceed(Mat Screenio$,Mat Screenio,[[Screencontrols]]) then
let Fnrecompileallscreens(Mat Screenio$,Mat Screenio,[[Screencontrols]])
let Fnprocesswindowsmenu=Menurecompile
end if
!
#Case# "test"
if Len(Trim$(Screenio$(Si_Screencode))) And Exists("screenio\"&Trim$(Screenio$(Si_Screencode))&".br") then
execute "system -C -M "&Fngetbrexe$&" -"&Fngetwbcfg$&" run screenio\"&Trim$(Screenio$(Si_Screencode))
let Fnprocesswindowsmenu=Menutest
else
let Msgbox("You must save your screen before testing it.")
end if
#Case# "help"
execute "system -C -M start http://brwiki.ads.net/index.php?title=ScreenIO_Library"
let Fnprocesswindowsmenu=Menuhelp
#Case# "about"
let Fnshowabout
let Fnprocesswindowsmenu=Menuabout
#Case# "events"
let Fnprocesswindowsmenu=Menuevents
#Case# "taborder"
let Fnprocesswindowsmenu=Menutaborder
#Case# "debug"
let Fnprocesswindowsmenu=Menudebug
#Case# "add field"
let Fnprocesswindowsmenu=Menufieldslist
#Case# "add textbox" # "add caption" # "add checkbox" # "add listview" # "add search box" # "add button" # "add picture" # "skip a space"
let Fnprocesswindowsmenu=Menuaddcontrol
#Case# "movemode"
let Fnprocesswindowsmenu=Menumovement
#Case# "debuglist"
let Fnprocesswindowsmenu=Menudebuglist
#Case# "setfgcolor"
let Fnprocesswindowsmenu=Menufgcolor
#Case# "setbgcolor"
let Fnprocesswindowsmenu=Menubgcolor
#Case# "selectlayout"
let Fnprocesswindowsmenu=Menuselectlayout
#Case# "resize screen"
let Fnresizescreen(Mat Screenio$,Mat Screenio,[[Screencontrols]])
#Case# "exit buttons"
let Fnaddexitbuttons(Mat Screenio$,Mat Screenio,[[Screencontrols]])
#Case# "search"
let fnPowerSearch
#Case# "codeexplore"
let fnCodeExplore(Mat ScreenIO$, mat ScreenIO, [[ScreenControls]])
#Case Else#
input Menu Status: Mat Status$
if Pos(Uprc$(Status$(Menu)),"C") then
if Pos(Uprc$(Status$(Menu)),"X") then
let Setenv(Menu$,"Y")
else
let Setenv(Menu$,"N")
end if
end if
#End Select#
fnend