Pregunta

Así que tengo este menú contextual que se resuelve la excepción de que el evento detrás de la actual selección de la opción de menú parece disparar varias veces. La primera vez que haga clic en él, se dispara una vez, luego dos veces, luego 3 veces. Así, en el ejemplo que acabo de dar, por 3 clics que habría disparado un total de 6 veces (1 + 2 + 3). ¿Por qué?

A continuación se muestra el código en la forma en que estoy creando los elementos del menú. Me desnudé hacia abajo a las piezas pertinentes; Omití cosas como .Tag, .Visible, y las propiedades .Caption. Estoy construyendo esto utilizando .NET 3.5 y VS 2008.

Gracias de antemano !!

Private WithEvents ActiveExplorerCBars As Office.CommandBars
Private app As New Outlook.Application

Private Sub ThisAddIn_Startup(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Startup
     ActiveExplorerCBars = app.ActiveExplorer.CommandBars
     AddHandler ActiveExplorerCBars.OnUpdate, AddressOf ActiveExplorerCBars_OnUpdate
End Sub

//This seems to get hit A LOT    
Private Sub ActiveExplorerCBars_OnUpdate()
    Dim bar As Office.CommandBar

    If IgnoreCommandbarsChanges Then Exit Sub

    bar = ActiveExplorerCBars.Item("Context Menu")

    If Not bar Is Nothing Then
        Dim addMenu As Boolean = False
        //this For loop just makes sure the context is only available when the user right-clicks over a mail item
        For Each mail As Outlook.MailItem In Application.ActiveExplorer().Selection
            addMenu = True
            Exit For
        Next
        If addMenu Then
            AddContextDropdown(bar)
        End If
    End If
End Sub

Private Sub AddContextDropdown(ByVal ContextMenu As Office.CommandBar)
    Dim RootPopup As Office.CommandBarPopup
    Dim popupTaskItem As Office.CommandBarPopup
    RootPopup = ContextMenu.FindControl(Type:=Office.MsoControlType.msoControlPopup, Tag:="Update task")

    If RootPopup Is Nothing Then
        ChangingBar(ContextMenu, Restore:=False)
        RootPopup = ContextMenu.Controls.Add(Type:=Office.MsoControlType.msoControlPopup)

        Dim thisTaskPopup As Office.CommandBarPopup
        popupTaskItem = ContextMenu.FindControl(Type:=Office.MsoControlType.msoControlPopup, Tag:=task.EntryID)
        If popupTaskItem Is Nothing Then
              popupTaskItem = RootPopup.Controls.Add(Type:=Office.MsoControlType.msoControlPopup)
              thisTaskPopup = popupTaskItem
              AddActionButtons(thisTaskPopup)
        End If
    End If
End Sub

Private Sub AddActionButtons(ByVal puItem As Office.CommandBarPopup)

    Dim puDeploy As Office.CommandBarPopup = puItem.Controls.Add(Type:=Office.MsoControlType.msoControlPopup)
    Dim btnActionItem As Office.CommandBarControl = puDeploy.Controls.Add(Type:=Office.MsoControlType.msoControlButton)
    Dim thisButton As Office.CommandBarButton = btnActionItem
    AddHandler thisButton.Click, AddressOf OnContextClick
End Sub

//Click event
Public Sub OnContextClick(ByVal ctrl As Microsoft.Office.Core.CommandBarButton, ByRef CancelDefault As Boolean)
   //This messagebox shows once the first time, twice the second, 3 times, etc
    MessageBox.Show("Clicked: " & ctrl.Caption)
End Sub
¿Fue útil?

Solución

lo he descubierto. tobrien, utilicé su último comentario como un vehículo para llegar a esta conclusión, sobre todo cuando usted dijo:

  

podría ser que su realidad la creación ADICIONAL (idénticamente signitured) devoluciones de llamada

El código que estoy utilizando para agregar el controlador es:

AddHandler thisButton.Click, AddressOf OnContextClick

¿Cómo podía estar signatured idéntica? Bueno, sólo hay un OnContextClick sub ... ¿Qué pasa con thisButton

For Each value As ActivityType.Request In [Enum].GetValues(GetType(ActivityType.Request))
        Dim btnActionItem As Office.CommandBarControl = puRequest.Controls.Add(Type:=Office.MsoControlType.msoControlButton)
        With btnActionItem
            .Tag = puRequest.Tag & "|" & value
            .Caption = [Enum].GetName(GetType(ActivityType.Request), value)
            .Visible = True
        End With
        Dim thisButton As Office.CommandBarButton = btnActionItem
        AddHandler thisButton.Click, AddressOf OnContextClick
    Next

Este código se ejecuta cuando se produce OnUpdate, que, como se sabe, ocurre todo el tiempo. Así que, en esencia, cada vez OnUpdate éxitos, estoy añadiendo un controlador adicional para el exacto mismo botón, no teniendo en cuenta que el botón es básicamente creado recientemente cada vez que se produce OnUpdate y que su controlador se almacena en la memoria.

Por lo tanto, es necesario hacer el control de botón único:

.Tag = puRequest.Tag & "|" & value & "|" & Now.ToBinary().ToString()

Me acaba de agregar un Now.ToBinary (). ToString () al final de la propiedad .Tag para asegurar que cada vez que el botón se crea para el usuario, que tiene una etiqueta única. Ahora los eventos son únicos y su único disparar una vez por cada clic.

tobrien, te soluto! A pesar de que en última instancia, respondió a mi propia pregunta, no fue sin su orientación. Gracias!

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top