5
respostas

A cada clique do botão uma macro diferente

Olá, pessoal. Tenho 3 macros diferentes e preciso que cada uma delas seja acionada unicamente quando clicar no botão. Deste jeito: Clica uma vez no botão: aciona macro 1 Clica mais uma vez no mesmo botão: aciona macro 2 Clica mais uma vez no mesmo botão: aciona macro 3 Clica mais uma vez no mesmo botão: volta para a macro 1 e segue o looping.

Como faço?

Obrigado

5 respostas

Você pode realizar os seguintes passos:

  1. Declarar uma variável global (isto é, fora da função que o botão irá executar). Variáveis globais são aquelas que são reconhecidas por todas as demais funções (e não somente no escopo de uma função). Para declarar uma global no VBA, basta declará-la como Public.

  2. Dentro da função, você coloca um if (ou um case) que testará o valor desta global. Dependendo de seu valor, ele executará uma macro diferente

  3. Ao final, modifica o valor da global para que da próxima vez que for executada, caia em outra condição dentro do if (ou do case).

No exemplo abaixo, eu fiz o teste com um case:

Public MinhaGlobal As Integer
MinhaGlobal = 1 ' Valor inicial - entrara no Case com valor 1

Private Sub CommandButton1_Click()
Select Case MinhaGlobal
    Case 1
        Call macro1
        MinhaGlobal = 2 ' No proximo clique, executara  macro2
    Case 2
        Call macro2
        MinhaGlobal = 3 '  No proximo clique, executara  macro3
    Case 3
        Call macro3
        MinhaGlobal = 1 '  No proximo clique, executara  macro1
End Select
End Sub

Obrigado, Jorge.

Eu não entendi bem o que deve ser feito. Pode me explicar novamente, por favor? Não entendi o que devo colocar no lugar do "1" em Minha Global e nem como o código vai entender que só deve disparar uma macro por clique e no final de tudo voltar a macro inicial. Grande abs

Oi, Priscila. Vou explicar usando o if porque talvez seja mais didático. E no lugar do MinhaGlobal do tipo inteiro, vou usar uma variável global denominada ProximaMacro onde ela vai guardar uma string (texto) que indicará qual macro será executada. O nome da função que executa o clique agora é SelecionaMacro_click.

Você só precisa de uma variável global de controle para guardar a indicação de qual macro será executada, seja indicando qual macro foi executada, seja indicando qual será a próxima macro que será executada. Não importa! No meu caso, isto é, no meu código, usei a global para representar qual a próxima a ser executada.


Public ProximaMacro As String 

ProximaMacro = "Macro1" 

Private Sub SelecionaMacro_Click()
If ProximaMacro = "Macro1"  Then
        ProximaMacro = "Macro2" 
        Call macro1
ElseIf ProximaMacro = "Macro2"  Then
        ProximaMacro = "Macro3" 
        Call macro2
ElseIf ProximaMacro = "Macro3" Then
          ProximaMacro = "Macro1" 
          Call macro3
End If
End Sub

Observe que `ProximaMacro" só terá os seguintes valores possíveis:

  • "Macro1"
  • "Macro2"
  • "Macro3"

O valor que esta variável representa, indicará onde no ìfa condição será atendida e, como consequência, qual macro será executada. A execução da macro propriamente dita se dá com o comandocall. Mas antes de chamar a macro, eu altero o valor daProximaMacropara que, da próxima vez que o botão for clicado, ele atenda ou parte doif` e, assim, executará outra macro e não a anterior.

Então observe o passo a passo de execução:

  1. Inicialmente, o vba lê a declaração da global ProximaMacro e atribui o valor Macro1 para ela;
  2. Quando o usuário clica no botão, a função SelecionaMacro_clck() será executada pela primeira vez;
  3. Dentro desta função há um if que verifica qual o valor da global ProximaMacro. ProximaMacro é igual a Macro1? Sim! (veja o passo 1). Então ele executa o que está dentro desta parte do if;
  4. Nesta parte do if, ele modifica o valor da global ProximaMacro para Macro2;
  5. Em seguida, executa a sua macro1 (eu não coloquei no código porque não sei quais são suas três macros que quer executar de forma alternada);
  6. Não tendo mais o que fazer no if, nem na função, encerra-se o algoritmo.

Agora imagine se o usuário clicar novamente no botão. O que acontecerá?

  1. Ele não vai executar novamente a declaração da ProximaMacro e atribuir o valor Macro1 para ela. Isto só é feito no início da execução da macro e somente uma vez! A variável global ProximaMacro já é reconhecida pelo vba e, inclusive, agora ela já está com o novo valor Macro2 que foi modificado no primeiro clique do botão.
  2. Ao entrar no if, verificará se o valor de ProximaMacro é igual a Macro1 (Macro2 = Macro1, retorna FALSE). É igual? NÃO!, pois ProximaMacro é igual a Macro2;
  3. Então, ainda na parte do if, ele vai testar o primeiro ElseIf e testar ProximaMacro = "Macro2. São iguais? SIM! Então ele modifica o valor de ProximaMacro para Macro3 e executará o call macro2 que executa a sua segunda macro;
  4. Ele sai do if e depois da função do clique do botão;

Se, mais uma vez, o usuário clicar no botão, quem será executado será a macro3. Mas antes disso, ele atribui valor Macro1 para ProximaMacro indicando que se o usuário clicar novamente, ele vai executar a macro1.

Então, há sempre esta ordem de execução:

macro1 -> macro2 -> macro3 -> macro1 -> macro2 -> macro3 -> macro1 -> ...

Oi Priscila, tudo bem?

A sua dúvida foi esclarecida?

Lembre-se de marcar a resposta que mais te ajudou como solução, caso contrário compartilhe sua dúvida para que possamos te ajudar, combinado?

Bons estudos. :)

O interessante seria talvez, acrescentar um alerta/sinalização de qual macro é a próxima ou no final do código de cada uma das 3 macros ajustar a global de volta pro valor 1... Imagino assim, cliquei uma vez, fui trabalhar com os resultados, a próxima vez que eu clicar a variável global estará na "posição 2"... lembrando que os efeitos das macros são definitivo... mas a ideia foi mto boa... qdo li a pergunta achei q seria algo mais dificil...