Title of Paper
Authors' Names
Abstract
Paper Body
1. Introduction
2. General
Conversion Guidelines
Heading = "My
Command"
Default = True
ians = MsgBox.YesNoCancel(Msg,
Heading, Default)
if (ians = Nil)
then
.... do something
end
if (ians.Not)
then
.... do something
else
.... do something
end
Dim Default
As Boolean
Dim ians
As Integer
Msg = "Okay
to continue ?"
Heading = "My
Command"
Default = True
Call avMsgBoxYesNoCancel(Msg,
Heading, Default, ians)
If (ians
= vbCancel) Then
.... do something
End If
If (ians
= vbNo) Then
.... do something
End If
If (ians
= vbYes) Then
.... do something
End If
If (a.NE.B) then x = y End
If (a <> b) then
x =
y
End If
"Error
Trapping":
Finally, a good feature to take advantage of in the VB/VBA
environment, which is not available in Avenue, is
the ability to trap errors.
Error trapping provides the developer a means to avoid
application runtime errors, which typically result in the application
to cease to operate properly. By avoiding application
runtime errors, the application can still be used to perform other
functions, should an error be encountered, rather than simply
"dying". This results in giving
the application a more professional appearance.
The code below demonstrates the use of error trapping:
'
Public Sub ShowErrorTrapping()
'
Dim pMxApp As IMxApplication
Dim pmxDoc As IMxDocument
Dim pActiveView As IActiveView
Dim pMap As IMap
'
' ---This
statement informs the application where to
' ---branch
when an error is detected in the procedure
On Error GoTo Errorhandler
'
' ---Get
the active view
Call avGetActiveDoc(pMxApp, pmxDoc,
pActiveView, pMap)
'
' ---do
something else
.
.
.
'
' ---At
this point, our work is done
Exit Sub
'
' ---Handle
any errors detected in the procedure
Errorhandler:
'
' ---Display
detected error number and a description
MsgBox "Error " & Err.Number & "
- " & Err.Description & _
Chr(13) & "Subroutine:
ShowErrorTrapping"
'
End Sub
Note that the introduction of comments in VB/VBA is the same as in Avenue with the exception that comments appear in the color green. In addition, syntax errors detected in VB/VBA appear in the color red as soon as the typing of a statement has been completed. This is quite a good feature, but it has a bothersome side effect. In addition to displaying the erroneous statement in red, VB/VBA also beeps and displays an error message box, which must be closed before the user can continue typing.
3. Application
- Document Avenue Wraps
vThemesList = theView.GetVisibleThemes
Dim pMxApp As
IMxApplication
Dim pmxDoc As
IMxDocument
Dim pActiveView
As IActiveView
Dim pMap As
IMap
Dim vThemesList
As New Collection
Call avGetActiveDoc(pMxApp,
pmxDoc, pActiveView, pMap)
Call avGetVisibleThemes(pmxDoc,
vThemesList)
The first point that needs to be
made, in reviewing the above code, is that in Avenue a developer
applied a request to an object, which resulted in another object
being created, vThemesList in the above Avenue example.
This approach is not possible using ArcObjects.
Therefore, to simulate the Avenue approach, Avenue Wraps
provides a subroutine or function to perform the function of the
Avenue request by using the argument list in the subroutine or
function to pass objects in and out.
The second point is that a List
object in Avenue translates to a Collection object in VB/VBA.
Note that List objects in Avenue are zero based, while
Collections begin at the index value 1.
For example, the first visible theme in vThemesList would
be found by issuing the following statement:
firstVTheme = vThemesList.Get(0)
while in VB/VBA
the statement would appear as:
firstVTheme = vThemesList.Item(1)
Note that the Avenue request Get
becomes Item in VB/VBA. So
that, the search for and revision of lists into collections, the
change of Get to Item, and the altering of the indexing could
be done at the start of the conversion process.
The final point is that the Avenue code contains two lines of code, while the VB/VBA code contains seven, the first five of which are declaration statements. Thus, even though there is a one to one correspondence between the Avenue requests and the wraparounds, the number of lines of VB/VBA code is greater than its Avenue counterpart due to the declaration statements. To make the VB/VBA code easier to read, it is suggested that all of the declaration statements be placed at the top of the procedure, rather than scattered throughout the subroutine or function. One procedure, which one may consider, is to introduce the declaration statements within the code where new variables are first encountered, and then, after the code has been tested, move the declaration statements to the top of the procedure in the same sequence of occurrence.
4. File
Input and Output Avenue Wraps
For example
the Avenue statement to open a file for writing would appear as:
aLineFile = LineFile.Make
(aFileName, #FILE_PERM_WRITE)
while using
Avenue Wraps, the statement would look like this:
Dim aFileName
As String
Dim aLineFile
Set aLineFile
= avLineFileMake(aFileName, "WRITE")
Note the
use of the word Set.
In VB/VBA when dealing with objects the keyword Set
is used to create an object. In this example, aLineFile
is a file system object.
In addition, in Avenue there were enumerations (predefined
values or constants), which certain requests recognized.
Avenue Wraps simulates enumerations by using strings
that reflect the enumeration, such as "WRITE" for "FILE_PERM_WRITE".
5. Theme
and Table Avenue Wraps
For example
the following Avenue code writes a value, 24, to a specific record,
12, in an FTab:
theTheme = theView.FindTheme("L_0ln")
theFTab = theTheme.GetFTab
col = theFTab.FindField("MAP")
rec = 12
theFTab.SetEditable(true)
theFTab.SetValue(col, rec, 24)
theFTab.SetEditable(false)
Using Avenue
Wraps, the above code could be converted as follows:
Dim pMxApp As
IMxApplication, pmxDoc As IMxDocument
Dim pActiveView
As IActiveView, pMap As IMap
Dim theTheme
As String
Call avGetActiveDoc(pMxApp,
pmxDoc, pActiveView, pMap)
theTheme = "L_0ln"
Call avGetFTab(pmxDoc,
theTheme, theFTab, pFeatCls, pLayer)
Call avSetEditable(pmxDoc,
theTheme, true)
Call avSetValue(pmxDoc,
theTheme, col, rec, 24)
Call avSetEditable(pmxDoc,
theTheme, false)
The Avenue
Wraps code shown above could be used on either an FTab or
a VTab, because the "wraparounds" check if the given
name passed in corresponds to a theme or to a table.
Note that the FindField request has a direct counterpart
in the ArcObjects world.
This is one of the very, very few examples where a "wraparound"
was not required.
As stated
above, the "wraparound", avSetValue, operates
on either an FTab or a VTab.
However, it cannot be used to store geometry (a feature's
shape). In this case
the "wraparound", avSetValueG, must be used. The reason is that when
storing attribute information with avSetValue,
the ArcObjects Value property
is used. However,
in order to store geometry (a feature's shape), the ArcObjects
Shape property needs to be used. Since there are two different
properties, two different wraparounds were created,
one to store attribute data and the other to store geometry.
Continuing with the example above, the Avenue code below would store a two-point line in record 12 of the FTab:
aShape = Polyline.Make({{20000.0,
20000.0, 30000.0, 25000.0}})
col = theFTab.FindField("SHAPE")
theFTab.SetEditable(true)
theFTab.SetValue(col, rec, aShape)
theFTab.SetEditable(false)
Using Avenue
Wraps, the above code could be converted as follows:
Set aShape =
avPolyline2Pt(20000#, 20000#,
30000#, 25000#)
Call avSetEditable(pmxDoc,
theTheme, true)
Call avSetValueG(pmxDoc,
theTheme, col, rec, aShape)
Call avSetEditable(pmxDoc,
theTheme, false)
In reviewing
the above Avenue Wraps code, note the # character in the
"wraparound" avPolyline2Pt. When a number is hard coded
with .0, .00, .000, etc., VB/VBA will remove the zeros and replace
them with the # character.
In addition, note that there is no direct Avenue counterpart
to the "wraparound", avPolyline2Pt. During CEDRA's conversion
process, in an effort to minimize the amount of recoding, certain
"wraparounds" were developed that do not have corresponding
Avenue requests, but satisfy a need in that they facilitate the
conversion process. In
the CEDRA software there were a lot of cases in which two point
lines were being created using the double left ({{) and the double
right (}}) brace characters.
Rather than using the "wraparound", CreateList
and adding point features to the lists (reference is made
to the Section 8 example), the "wraparound", avPolyline2Pt
was created.
As a matter
of fact, there are a number of "wraparounds" which do
not have an Avenue counterpart, but when used, greatly help in
the conversion of Avenue to VB/VBA code.
Finally,
a good feature to take advantage of is the Undo / Redo capabilities
of ArcObjects. The wraparound,
avSetEditable, when used with
the false parameter on a theme will not terminate the editing
of the theme. Rather, the wraparound
only flushes any buffered writes there may be on the theme.
Thus, the theme remains in an editable state. This is intentionally done
so that the developer can take advantage of the Undo / Redo capabilities. To do so, the wraparounds,
avStartOperation and avStopOperation,
should be used. These
wraparounds begin and terminate an edit operation
which is added to the Editors operation stack.
This enables the end user to perform an Undo or Redo operation.
The avStartOperation subroutine is called
after the theme has been made editable. The avStopOperation
subroutine is called when the desired editing has been completed.
A call to the avStopOperation
subroutine must be made if a call to the avStartOperation
subroutine has been issued.
There is no limit to the number of times these subroutines
can be called within an edit session. The wraparound,
avStopEditing, will terminate
the Editor saving any edits that may have been made.
6. Feature
Selection Avenue Wraps
theTheme = theView.FindTheme("L_0ln")
theFTab = theTheme.GetFTab
col = theFTab.FindField("Deposits")
sel = theFTab.GetSelection
total = 0.0
for each rec in sel
deposit
= theFTab.ReturnValue(col, rec)
total = total + deposit
end
Using Avenue
Wraps, the above code could be converted as follows:
Dim pMxApp As
IMxApplication, pmxDoc As IMxDocument
Dim pActiveView
As IActiveView, pMap As IMap
Dim theTheme
As String
Call avGetActiveDoc(pMxApp,
pmxDoc, pActiveView, pMap)
theTheme = "L_0ln"
Call avGetFTab(pmxDoc,
theTheme, theFTab, pFeatCls, pLayer)
Call avGetSelection(pmxDoc,
theTheme, sel)
Call avGetSelectionIDs(sel,
selList)
total = 0#
In reviewing
the above Avenue Wraps code, note the use of the "wraparound",
avGetSelectionIDs. This "wraparound"
returns a collection of OIDs (object identification numbers) for
each of the selected features.
So that, rather than looping on the selected set, sel,
as was done in Avenue, a loop is performed on the collection,
selList. An
OID is extracted from selList and a feature extracted from
the pFeatCls object. Using the feature, pFeat,
the deposit value is extracted and added to total.
This example illustrates the main difference between Avenue
and ArcObjects, in that, in Avenue manipulation of data was performed
on FTab or VTab objects.
Using ArcObjects, manipulation of data is performed using
the IFeature interface, for FTab's, and the IRow interface, for
VTab's. Obviously,
this difference poses an obstacle in converting Avenue code, but
using the "wraparound", avGetSelectionIDs, a
work-around is fairly easily achieved.
7. Message
and Menu Boxes Avenue Wraps
MsgBox.Info("A sample
message string.", "MsgBox Test")
would be converted
using Avenue Wraps as:
Call avMsgBoxInfo("A
sample message string.", "MsgBox Test")
Internally,
avMsgBoxInfo calls another subroutine
passing information, which denotes that the Info request is to
be simulated. By taking
the approach to programmatically modify a single form, we avoid
the alternative of having to create a unique form for every type
of dialog box that is used in the CEDRA software.
So that, the Avenue requests Warning, YesNo and YesNoCancel,
as well as Info, all end up calling the same subroutine which
in turn uses the same Avenue Wraps form, MessageBox.
Likewise, the other Avenue message box requests, Choice,
Input, List, MultiInput and MultiList all end up using the Avenue
Wraps form, VDialogBox. Thus, based upon what information
is passed into the controlling subroutine, the appropriate dialog
box is displayed.
In addition, to simply the conversion of the standard MsgBox requests, additional "wraparounds" were developed to provide for more sophisticated dialog boxes, such as dialog boxes that could contain "dr