E_ITEMC.DLG BEGIN 101 0.00 0.00 11.00 18.00 v CBOX 102 0.50 1.50 1.00 1.50 v LTEXT 103 0.50 4.00 1.00 11.00 f CBOX 104 1.50 1.50 1.00 1.50 v LTEXT 105 1.50 4.00 1.00 11.00 f CBOX 106 2.50 1.50 1.00 1.50 v LTEXT 107 2.50 4.00 1.00 11.00 f CBOX 108 3.50 1.50 1.00 1.50 v LTEXT 109 3.50 4.00 1.00 11.00 f CBOX 110 4.50 1.50 1.00 1.50 v LTEXT 111 4.50 4.00 1.00 11.00 f CBOX 112 5.50 1.50 1.00 1.50 v LTEXT 113 5.50 4.00 1.00 11.00 f CBOX 114 6.50 1.50 1.00 1.50 v LTEXT 115 6.50 4.00 1.00 11.00 f CBOX 116 7.50 1.50 1.00 1.50 v LTEXT 117 7.50 4.00 1.00 11.00 f PBUT -118 0.50 15.00 1.00 2.00 v ^ PBUT -119 7.50 15.00 1.00 2.00 v v PBUT -120 9.25 1.00 1.50 8.00 v OK PBUT -121 9.25 9.00 1.50 8.00 v Cancel END If the list of items exceeds the size of the dialog box, the "^" and/or "v" buttons are enabled to allow the user to scroll through the list. (Another dialog box, E_ITEMR.DLG, replaces CBOX widgets with RBUT, enabling a single choice item picker.) Now let's use GUITOOL directives to create and populate the dialog and return the response:Thanks to GUITOOL, the only difficulty is maintaining the check state of the items, which is handled by routine CHKITEM:*ROUTINE getitem e_itemc.dlg 1 e_itemr.dlg 1 *REM arg1 = C or R (check box or radio button) *REM arg2 = title for dialog box &define i -9 &var &define wtype -11 &var &define title -12 &var &define numit -13 &var &define pos -14 &var &define resp -15 &var &define wksp -16 &var &define temp -19 &var &rem **** load items starting at variable 130 &extract [wtype] -1 1 &value [title] -2 &value [wksp] WKSP &openw [wksp]t$temp.lis ITEMS &closew &open [wksp]t$temp.lis error &sv [numit] 0 &while &do &read [temp] [break] &extract -1 [temp] 1 &if &nm %-1 &do &extract -2 [temp] 2 &extract -3 [temp] 3 &extract -4 [temp] 4 &extract -5 [temp] 5 &sv [temp] "%-2 %-3 %-4 %-5 0" &value %<[numit] + 130> [temp] &inc [numit] &end &end &close & DEL [wksp]t$temp.lis &rem **** initialize and open dialog &openw [winfile] *W S 101 [title] &sv [i] 1 &while &rn [i] 1 %<[numit] min 8> &do &extract [temp] %<[i] + 129> 1 *W S %<[i] * 2 + 101> [temp] &inc [i] &end &sv [pos] 1 *W G 118 &if &eq %<[numit] max 8> 8 &do *W G 119 &else *W E 119 &end &if &rn [numit] 1 7 &do &cv [i] [numit] + 1 &while &rn [i] 1 8 &do *W G %<[i] * 2 + 100> &inc [i] &end &end &closew &sv [resp] CANCEL &if &eq C [wtype] &do *OPEN e_itemc.dlg &else *OPEN e_itemr.dlg &end &rem **** pick loop *PICK 118 &openw [winfile] &if &eq %<[pos] min 7> [pos] &do &sv [temp] 1 &else &cv [temp] [pos] - 7 &end &if &eq [temp] 1 &do *W G 118 &end *W E 119 &r chkitem [pos] [temp] [wtype] [numit] &closew &sv [pos] [temp] *PICK 119 &openw [winfile] &if &eq %<( [pos] + 14 ) max [numit] > [numit] &do &cv [temp] [pos] + 7 &else &cv [temp] [numit] - 7 &end *W E 118 &if &eq %<[temp] + 7> [numit] &do *W G 119 &end &r chkitem [pos] [temp] [wtype] [numit] &closew &sv [pos] [temp] *PICK 120 &sv [resp] OK *CLOSE *PICK 121 *CLOSE *ENDPICK &rem **** generate reply &if &eq CANCEL [resp] &do &return [resp] &end &r chkitem [pos] [pos] [wtype] [numit] &sv [i] 1 &sv [resp] 0 &while &rn [i] 1 [numit] &do &extract [temp] %<[i] + 129> 5 &if &eq [temp] 1 &do &inc [resp] &extract -1 %<[i] + 129> 1 &extract -2 %<[i] + 129> 2 &extract -3 %<[i] + 129> 3 &extract -4 %<[i] + 129> 4 &sv %<[resp] + 500> "%-1 %-2 %-3 %-4" &end &inc [i] &end &return [resp] &rem **** I/O error trap &label error &type "I/O Error" &sv [resp] CANCEL &return [resp]
*ROUTINE chkitem
*REM check and set state of items
&define i -9 &var
&define old -11 &var
&define new -12 &var
&define wtype -13 &var
&define numit -14 &var
&define name -15 &var
&define state -16 &var
&define unchk -17 &var
&value [old] -1
&value [new] -2
&value [wtype] -3
&value [numit] -4
&sv [i] 1
&sv [unchk] 0
&while &rn [i] 1 8 &do
&value -1 %<[i] * 2 + 100>
&cv [unchk] [unchk] + %-1
&inc [i]
&end
&sv [i] 1
&while &rn [i] 1 [numit] &do
&if &rn [i] [old] %<[old] + 7> &do
&value [state] %<[i] - [old] * 2 + 102>
&extract -1 %<[i] + 129> 1
&extract -2 %<[i] + 129> 2
&extract -3 %<[i] + 129> 3
&extract -4 %<[i] + 129> 4
&sv %<[i] + 129> "%-1 %-2 %-3 %-4 [state]"
&elseif &eq R [wtype] &and &ne [unchk] 0 &do
&extract -1 %<[i] + 129> 1
&extract -2 %<[i] + 129> 2
&extract -3 %<[i] + 129> 3
&extract -4 %<[i] + 129> 4
&sv %<[i] + 129> "%-1 %-2 %-3 %-4 0"
&end
&if &ne [old] [new] &and &rn [i] [new] %<[new] + 7> &do
&extract [name] %<[i] + 129> 1
&extract [state] %<[i] + 129> 5
*W S %<[i] - [new] * 2 + 102> [state]
*W S %<[i] - [new] * 2 + 103> [name]
&end
&inc [i]
&end
&return
Thus when a dialog is scrolled, the check state of items is preserved:

Similarly, when the R option is used and an item is checked, the previously checked item is unchecked. Should the number of items be less than 8, the appropriate widgets are grayed:

When the "OK" button is clicked, GETITEM returns the number of items picked (0 if none) and loads those item names and definitions into SML variables starting at number 501 (a distinct advantage over the old method, which returned a string of item names that was limited to 80 characters). The number in turn may be passed to a FORMS or CALC routine.
One disadvantage of this approach is that a separate dialog box is required for a radio button list. Also, supporting the arrow buttons requires a bit of code. Nonetheless, by taking this approach I'm simplifying the dialog-related code, and by enhancing the returned information content I'm able to apply this routine to more situations.
The basic strategy is to restrict variable assignment as much as possible; if an application can read a value using &value or SHOW, there's no need to maintain a global variable. The following example applies the above approach to the ETOOL application developed in the previous issue (V6N4); only a few edit parameters are saved, just enough to give you an idea of what's involved. First, lets make some changes to the beginning of E_MAIN.MNU:
POPUP Project MENUI Open..., OPENP MENUI Save, SAVEP MENUI Save As..., SAVEPAS POPEND POPUP Cover MENUI Open..., SETCOV MENUI Save, SAVE MENUI Switch, SWITCH MENUI Remove, REMCOV MENUI Back Cover, BACKCOV MENUI Remove Back, REMBACK POPENDThen add some *PICK entries to the menu loop:
*PICK OPENP &r openp *PICK SAVEP &r savep *PICK SAVEPAS &r savepasAll three routines store the project file name in variable 51. Variable 52 is used as a flag to indicate whether changes have been made in pertinent project settings (e.g. setting an edit cover or back cover). Let's look at routine SAVEP first:
*ROUTINE savep
*REM **** save session settings
&define project 51 &var
&define saved 52 &var
&define i -11 &var
&define editn -12 &var
&define backn -13 &var
&define temp -19 &var
&define winrtn 1 &var
&if &eq "x[project]" "x" &do
WIN FILE 3 etp 'Save Project'
&if &eq "x[winrtn]" "x" &do
&return
&end
&value [project] [winrtn]
&end
&openw [project]
*REM **** save editc and backc info
&sv [i] 1
&sv [editn] 0
&sv [backn] 0
&while &rn [i] 1 4 &do
SHOW BACKCOVER %[i] -1
&if &ne "x%-1" "x" &do
&inc [backn]
&value [temp] %<34 + [i]>
*W BACKC %-1 [temp]
*W &sv %<34 + [backn]> [temp]
&end
SHOW EDITCOVER %[i] -1
&if &ne "x%-1" "x" &do
&inc [editn]
&value [temp] %<30 + [i]>
*W EDITC %-1
*W &sv %<30 + [editn]> [temp]
&end
&inc [i]
&end
&sv -1 X
SHOW EDITCOVER 0 -1
SHOW EDITFEAT -2
&if &ne X %-1 &do
*W EDITC %-1
*W EDITF %-2
&end
*REM **** save draw settings
SHOW DRAWE -1 -2 -3 -4 -5
*W DRAWE ARC %-1 NODE %-2 LABEL %-3 TIC %-4 ANNO %-5
SHOW SETDRAWS -1 -2
*W SETDRAWS %-1
*W SETDRAWS %-2
SHOW NODEC NODE -1
*W NODEC NODE %-1
SHOW NODEC DANGLE -1
*W NODEC DANGLE %-1
SHOW NODEC PSEUDO -1
*W NODEC PSEUDO %-1
SHOW BACKE -1 -2 -3 -4 -5
*W BACKE ARC %-1 NODE %-2 LABEL %-3 TIC %-4 ANNO %-5
SHOW LINESET -1
*W LINESET %-1
SHOW MARKERSET -1
*W MARKERSET %-1
SHOW TEXTSET -1
*W TEXTSET %-1
*REM **** save edit settings
SHOW MAPE -1 -2 -3 -4
*W MAPE %-1 %-2 %-3 %-4
SHOW EDITD -5
SHOW SNAPD -6
SHOW WEED -7
SHOW GRAIN -8
MAPE ZOOM 2
SHOW EDITD -15
SHOW SNAPD -16
SHOW WEED -17
SHOW GRAIN -18
MAPE %-1 %-2 %-3 %-4
&if &ne %-5 %-15 &do
&sv -5 DEFAULT
&end
&if &ne %-6 %-16 &do
&sv -6 DEFAULT
&end
&if &ne %-7 %-17 &do
&sv -7 DEFAULT
&end
&if &ne %-8 %-18 &do
&sv -8 DEFAULT
&end
*W EDITD %-5
*W SNAPD %-6
*W WEED %-7
*W GRAIN %-8
*REM **** wrap up
*W DRAW
&closew
&sv [saved] YES
&return
In this example, variables 31-34 store the current edit feature for each
edit cover, and 35-38 store the symbol for each back cover (more on this
in the next issue). Because SHOW only returns a number for the edit
parameters EDITD, SNAPD, WEED, and GRAIN, the routine changes the map
extent temporarily to see whether they are set to DEFAULT. Note also
that the [winrtn] alias needs to be defined: if a *ROUTINE directive
does not declare any dialogs, GUITOOL will not automatically define the
[winrtn] and [winfile] aliases.Since routine SAVEP saves an executable SML file, routine OPENP requires very little coding:
*ROUTINE openp
&define project 51 &var
&define saved 52 &var
&define winrtn 1 &var
&if &eq [saved] NO &do
WIN MB 3 'Save Project Changes?'
&if &eq [winrtn] YES &do
&r savep
&elseif &eq [winrtn] CANCEL &do
&return
&end
&end
WIN FILE 1 etp 'Load Project'
&if &eq "x[winrtn]" "x" &do
&return
&end
&value [project] [winrtn]
&sv -1 1
&sv -2 .FALSE.
&sv -3 .FALSE.
&while &rn %-1 1 4 &do
SHOW EDITCOV %-1 -4
&if &ne "x%-4" "x" &do
&sv -2 .TRUE.
&end
SHOW BACKCOV %-1 -4
&if &ne "x%-4" "x" &do
&sv -3 .TRUE.
&end
&inc -1
&end
&if &eq %-2 .TRUE. &do
REMOVEEDIT ALL
Y
&end
&if &eq %-3 .TRUE. &do
REMOVEBACK ALL
&end
&r [project]
&sv [saved] YES
&return
Note that the routine checks for the presence of edit and/or back
coverages and removes them if necessary. Routine SAVEPAS requires even
less code:
*ROUTINE savepas *REM **** save project settings as new file &define project 51 &var &define winrtn 1 &var WIN FILE 3 etp 'Save Project' &if &eq "x[winrtn]" "x" &do &return &else &value [project] [winrtn] &r savep &end &returnNow we're going to take a look at how that information is maintained when opening and removing edit and back coverages. When opening an edit coverage, the user is automatically asked to set the edit feature, so the only change necessary is to add some lines at the end of routine SETEDITF:
*REM **** store edit feature
&sv -2 1
SHOW EDITCOVER 0 -3
&while &rn %-2 1 4 &do
SHOW EDITCOVER %-2 -4
&if &eq "x%-4" "x%-3" &do
&value %<%-2 + 30> -1
&break
&end
&inc -2
&end
&return %-1
The four edit cover slots are searched for a match to editcover 0, and
the edit feature (variable -1) is stored in the appropriate location.
Also, the following line is placed at the end of the "*PICK SETCOV
SETFEAT 106" entry in routine ETOOL:
&sv [saved] NOIn the last article some entries were added to E_MAIN.MNU to add back coverages and remove edit or back coverages; now we'll add some *PICK directives to routine ETOOL to support them:
*PICK REMCOV *OPEN remcov H EDIT *PICK BACKCOV *OPEN setbackc H &sv [saved] NO *PICK REMBACK *OPEN remcov H BACKLet's look at routine SETBACKC first. It uses a new dialog named E_SETBC.DLG:
BEGIN 0 0.00 0.00 6.00 24.00 v Back Coverage EBOX 101 0.50 1.00 1.50 20.00 v PBUT -102 0.50 21.50 1.50 1.50 v » LTEXT 0 2.50 1.00 1.00 8.00 v Symbol: EBOX 103 2.50 9.00 1.50 6.00 v 2 PBUT -104 2.50 15.50 1.50 1.50 v » PBUT -105 4.25 1.00 1.50 8.00 v OK PBUT -106 4.25 9.00 1.50 8.00 v Cancel

The code for routine SETBACKC is as follows:
*ROUTINE setbackc
e_setbc.dlg 1
*REM **** get back cover
&define i -10 &var
&define pos -11 &var
&sv [i] 1
&sv [pos] 0
&while &rn [i] 1 4 &do
SHOW BACKCOVER %[i] -2
&if &eq "x%-2" "x" &do
&cv [pos] 34 + [i]
&break
&end
&inc [i]
&end
&if &eq [pos] 0 &do
WIN MB 1 'No more room for back coverages'
&return
&end
&sv -1
&sv -2
*OPEN e_setbc.dlg
*PICK 102
*FILE 101 C * 'Enter coverage'
*PICK 105
&sv -1 %101
&sv -2 %103
*CLOSE
*PICK 106
*CLOSE
*ENDPICK
&if &eq "x%-1" "x" &do
&return
&end
&if &eq "x%-2" "x" &do
&sv -2 1
&end
BACKC %-1 %-2
&value %[pos] -2
&sv [saved] NO
&return
The code is almost identical to routine SETEDITC save that it supports
an extra widget (103) for the back symbol. (Support for widget 104,
launching the symbol picker, will be discussed in the next article.)
In fact, it would be more efficient to combine SETEDITC and SETBACKC, as
is done in routine REMCOV. Routine REMCOV uses E_GETCC.DLG:
BEGIN 101 8.00 40.00 8.00 36.00 v CBOX 102 1.00 1.00 1.00 1.50 v LTEXT 103 1.00 4.00 1.00 31.00 v CBOX 104 2.00 1.00 1.00 1.50 v LTEXT 105 2.00 4.00 1.00 31.00 v CBOX 106 3.00 1.00 1.00 1.50 v LTEXT 107 3.00 4.00 1.00 31.00 v CBOX 108 4.00 1.00 1.00 1.50 v LTEXT 109 4.00 4.00 1.00 31.00 v PBUT -110 6.00 1.00 1.50 8.00 v OK PBUT -111 6.00 9.00 1.50 8.00 v Cancel

*ROUTINE remcov
e_getcc.dlg 1
*REM **** remove edit or back cover
&define type -8 &var
&define i -9 &var
&value [type] -1
&openw [winfile]
&if &eq [type] EDIT &do
*W S 101 Remove Edit Coverage(s)
&else
*W S 101 Remove Back Coverage(s)
&end
&sv [i] 1
&while &rn [i] 1 4 &do
&if &eq [type] EDIT &do
SHOW EDITCOV %[i] -1
&else
SHOW BACKCOV %[i] -1
&end
&if &eq "x%-1" "x" &do
*W G %<[i] * 2 + 100>
&else
&value %<-10 - [i]> -1
&rem &value -2 -1 %
*W S %<[i] * 2 + 101> %-1
&end
&inc [i]
&end
&closew
&sv -1 CANCEL
*OPEN e_getcc.dlg
*PICK 110
&sv -1 OK
*CLOSE
*PICK 111 49
*CLOSE
*ENDPICK
&if &eq %-1 CANCEL &do
&return
&end
&sv [i] 1
&while &rn [i] 1 4 &do
&value -1 %<[i] * 2 + 100>
&if &eq %-1 1 &do
&value -2 %<-10 - [i]>
&if &eq [type] EDIT &do
REMOVEE %-2
&type " "
Y
&sv %<30 + [i]> NONE
&else
REMOVEB %-2
&sv %<34 + [i]> 0
&end
&end
&inc [i]
&end
&sv [saved] NO
&return
First, the routine sets the title of the dialog box. Then it searches
through the four slots of edit or back coverages: where one is filled,
the appropriate text widget is assigned that value, otherwise the widget
is left blank and the checkbox grayed. If a particular coverage is
removed, its edit feature or back symbol variable is cleared.

ETSTART.SML, which should reside in %ARC%\UTOOL, contains the following code:
&value 51 -1 &sv 52 "ETP" arceditw etool QUITAll that's left is to write some code so that ETOOL knows a project is being launched. First, the following line in routine ETOOL:
DRAWE ARC LABEL NODE ERRORS TIC IDSis replaced with:
&r initRoutine INIT has the following code:
*ROUTINE init &sv -1 1 &while &rn %-1 1 4 &do &sv %<%-1 + 30> NONE &sv %<%-1 + 34> 0 &inc -1 &end &if &ne "x[saved]" "xETP" &do &sv [project] &end &if &ne "x[project]" "x" &do &r [project] &else DRAWE ARC LABEL NODE ERRORS TIC IDS BACKE ARC &end &sv [saved] YESThus, when a project file is opened in Explorer, its name is passed to ETSTART.SML, which assigns the filename to variable 51 and the "ETP" flag to 52. Routine INIT, after clearing the edit feature and back symbol variables, runs the project file if the "ETP" flag is set.
Return to ArcTips page