vb.net - trick to make dropdown/combobox work?

3843
5
02-01-2011 08:43 AM
maxsteinbrenner
New Contributor II
hey everyone,

i did recently get my first simple button module to work (sort of) with dotnet but now i am on to trying to get some other projects converted over from VBA...

i am now trying to convert one of my old projects which uses a drop-down from VBA to .net and i must be missing something?

here is the main chunk of the code (with a few of the subroutines left out since they don't seem relevant)

Imports ESRI.ArcGIS.ArcMapUI
Imports ESRI.ArcGIS.Carto
Imports ESRI.ArcGIS.Catalog
Imports ESRI.ArcGIS.DataSourcesGDB
Imports ESRI.ArcGIS.DataSourcesFile
Imports ESRI.ArcGIS.DataSourcesRaster
Imports ESRI.ArcGIS.Display
Imports ESRI.ArcGIS.Geodatabase
Imports ESRI.ArcGIS.Geometry
Imports ESRI.ArcGIS.SystemUI
Imports ESRI.ArcGIS.esriSystem

Public Class CrewChiefSelect
    Inherits ESRI.ArcGIS.Desktop.AddIns.ComboBox

    Public Sub New()
        'Set Active Data Frame to "Main"
        SetActiveDataFrame()

        'Populates CrewChief combo box with values from CrewChief layer and sorts them
        Dim pMxDoc As IMxDocument
        pMxDoc = My.ArcMap.Document

        Dim pMap As IMap
        pMap = pMxDoc.FocusMap

        Dim pLayer3 As IFeatureLayer
        Dim pData As IDataStatistics
        Dim pCursor As ICursor
        Dim pEnumVar As IEnumVariantSimple
        Dim value As Object
        Dim pTable As ITable

        Me.Clear()

        'Pull information for dropdown box
        pLayer3 = pMap.Layer(2)
        pTable = pLayer3
        pCursor = pTable.Search(Nothing, False)

        Dim pRow As IRow

        pData = New DataStatistics
        'Dim DISDAYCC As String

        pRow = pCursor.NextRow
        pData = pRow.Value(6)


        'pData.Field("DISDAYCC")
        pData.Cursor = pCursor
        pEnumVar = pData.UniqueValues
        value = pEnumVar.Next
        Dim DiagCollection As New Collection
        'Dim Inst

        Do Until IsNothing(value)
            If value = " " Then
                value = pEnumVar.Next
            Else
                DiagCollection.Add(CStr(value))

            End If
            value = pEnumVar.Next
        Loop

        'DiagCollection = SortCollection(DiagCollection)

        For Each Item In DiagCollection
            Me.Add(Item)
        Next

    End Sub

    Protected Sub Update(ByVal newIndex As Long)
        Enabled = My.ArcMap.Application IsNot Nothing
        ClearAll()

        AddLayers()

        Dim pMxDoc As IMxDocument
        pMxDoc = My.ArcMap.Document

        Dim pMap As IMap
        pMap = pMxDoc.FocusMap

        Dim pLayout As IPageLayout
        pLayout = pMxDoc.PageLayout

        Dim pActiveView As IActiveView
        pActiveView = pMap

        'Query for selecting points in CrewChief boundary
        Dim strQuery As String
        strQuery = """DISDAYCC""" & " = " & "'" & Me.Value & "'"


        'Set pLayer to 2nd CrewChief polygon Layer
        Dim pLayer As IFeatureSelection
        pLayer = pMap.Layer(2)

        'Set pLayer2 to 1st CrewChief District polygon Layer
        Dim pLayer2 As IFeatureLayerDefinition
        pLayer2 = pMap.Layer(1)

        'Selects queried polygon from CrewChief layer
        Dim pFilter As IQueryFilter
        pFilter = New QueryFilter

        pFilter.WhereClause = strQuery

        pLayer.SelectFeatures(pFilter, esriSelectionResultEnum.esriSelectionResultNew, False)
        '
        '    Dim pBlueColor As IRgbColor
        '    Set pBlueColor = New RgbColor
        '    pBlueColor.RGB = RGB(0, 112, 225)
        '
        '    Set pLayer.SelectionColor = pBlueColor

        'Definition Query to Select CrewChief (Definition query to only display selected CrewChief boundary in the first crewchief layer so it thicker than other CrewChief boundaries)
        pLayer2.DefinitionExpression = strQuery

        'Selects queried Crewchief to zoom to the level of that selected CrewChief boundary
        Dim pLayer3 As IFeatureLayer
        pLayer3 = pMap.Layer(2)

        Dim pFSel As IFeatureSelection
        pFSel = pLayer3

        Dim pSelSet As ISelectionSet
        pSelSet = pFSel.SelectionSet

        Dim pEnumGeom As IEnumGeometry
        Dim pEnumGeomBind As IEnumGeometryBind

        pEnumGeom = New EnumFeatureGeometry
        pEnumGeomBind = pEnumGeom
        pEnumGeomBind.BindGeometrySource(Nothing, pSelSet)

        Dim pGeomFactory As IGeometryFactory
        pGeomFactory = New GeometryEnvironment

        Dim pGeom As IGeometry
        pGeom = pGeomFactory.CreateGeometryFromEnumerator(pEnumGeom)

        'Makes an envelope for selected features to determine proper page layout orientation
        Dim pEnvelope As IEnvelope

        pEnvelope = pGeom.Envelope

        pEnvelope.XMax = pEnvelope.XMax + 100
        pEnvelope.XMin = pEnvelope.XMin - 100
        pEnvelope.YMax = pEnvelope.YMax + 100
        pEnvelope.YMin = pEnvelope.YMin - 100

        pMxDoc.ActiveView = pMap
        pMxDoc.ActiveView.Extent = pEnvelope

        'Determine the envelope ratio (for setting layout)
        Dim intEnvelopeHeight As Long
        intEnvelopeHeight = pEnvelope.YMax - pEnvelope.YMin

        Dim intEnvelopeWidth As Long
        intEnvelopeWidth = pEnvelope.XMax - pEnvelope.XMin

        If intEnvelopeHeight > intEnvelopeWidth Then
            strLayoutType = "Portrait"

        ElseIf intEnvelopeHeight < intEnvelopeWidth Then
            strLayoutType = "Landscape"

        Else
            strLayoutType = "Portrait"

        End If

        'Clear slection after zoom level is established

        pMap.ClearSelection()

        AddDataFrame()

        AddTitle()

        CreateAndAddNewMap()

        InsertLogo()

        ClearSelection()

    End Sub


the code shows no errors when i debug it but when i add the drop-down into the arcmap project with the data it should reference it is grayed out...

any help is much appreciated!

thanks,

max
0 Kudos
5 Replies
NeilClemmons
Regular Contributor III
I haven't done much at all with addins but if you were doing this the old way you would be implementing a tool control.  This is done by implementing ICommand and IToolControl.  You would enable/disable the control using the ICommand.Enabled property.  The addin probably has something similar.  Look for an Enabled property that you can implement or set.
0 Kudos
BrianBottoms
New Contributor
I only have suggestions �?? no real answers. 

I believe the Sub New is called when ArcMap starts up and creates the combo box, so your code may not fire unless you double clicked on a specific mxd to launch ArcMap i.e. launching a new/empty version of ArcMap then opening a specific mxd will not result in New being fired twice.

If you haven�??t already, I would run the application in debug mode to see if the code is running OK.  I wonder if you are ever making it to the Update routine that returns Enabled = True.

Try putting all your code in Try Catch blocks with error messages.  Also, I would play with New and Update subs to make sure they fire when you expect and if this is the best place to put your code.

Have you run a simple test Add-In combobox that does almost nothing to make sure you are creating your Add-In projects correctly?  I ran into a variety of difficulties initially playing with Add-Ins when doing things like writing an Editor Extension with a dockable window.  I found that it was best to let the new project wizard in Visual Studio for ArcMap Add-Ins do as much as possible and adding controls directly to the Config.esriaddinx is error prone (at least for me).

'Simple test...
Public Class cboTest
    Inherits ESRI.ArcGIS.Desktop.AddIns.ComboBox

    Public Sub New()
        Try

            'Simple test
            Dim x As Integer
            For x = 0 To 10
                Me.Add(CStr(x))
            Next

        Catch ex As Exception
            Debug.Print(ex.Message)
        End Try

    End Sub

    Protected Overrides Sub OnUpdate()
        Enabled = My.ArcMap.Application IsNot Nothing

    End Sub
End Class


Brian
0 Kudos
maxsteinbrenner
New Contributor II
Brian,

thanks for your suggestions.

luckily yesterday i was able to borrow one of our developers and painfully introduce him into how ArcGIS does vb.net

anyhow after playing with it for most of the day we came up with a routine that will load the data into the combobox only once (which was tricky and required boolean to keep the code from running repeatedly) and then fire the other subroutine when a value was chosen.

the sake of anyone lse trying this, i will post the initial code we finally came up with... but honestly i am not sure if this is the best wat of doing it.

Public Class CrewChiefSelect2
    Inherits ESRI.ArcGIS.Desktop.AddIns.ComboBox

    Private IsUpdate As Boolean = True
    Private ListValue As String = String.Empty

    Public Sub New()

    End Sub

    Protected Overrides Sub OnSelChange(ByVal cookie As Integer)
        MyBase.OnSelChange(cookie)


        ListValue = Me.Value

        If Not (ListValue = String.Empty) Then
            Update(ListValue)
        End If



    End Sub

    Protected Overrides Sub OnUpdate()
        Enabled = My.ArcMap.Application IsNot Nothing

        If IsUpdate Then

            LoadData()

            IsUpdate = False
        End If
    End Sub


these call other subroutines, the one for the initial population of the dropdown LoadData, and then the Update subroutine that fires when a value is chosen from the dropdown.

i can't believe it should require all this when it was so simple in VBA with just two routines one for the document open and the other for the selection change but hey at least it works. if anyone has a simpler way to get this done i would love to hear it.

thanks,

max
0 Kudos
ScottDismukes
New Contributor
Is this for an Add-In?  Make sure your XML has editable="true" in the combobox tag.
0 Kudos
JoePartlow
New Contributor III
Is this for an Add-In?  Make sure your XML has editable="true" in the combobox tag.


This was extremely helpful to me.  Thanks.
0 Kudos