Click here to load reader
Upload
everton-nobre
View
521
Download
50
Embed Size (px)
Citation preview
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
Série “Como Fazer”
Formulários no Excel Utilizando VBA:
Listbox e Combobox
Parte 1
por Robert Friedrick Martim
Série “Como Fazer”: Criando menus, barras de comando e botões personalizados no Excel
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
i
Nota sobre direitos autorais Este eBook é de autoria de Robert F Martim, sendo comercializado através do site
www.juliobattisti.com.br ou através do site de leilões Mercado Livre:
www.mercadolivre.com.br.
Ao adquirir este eBook você tem o direito de lê-lo na tela do seu computador e de imprimir
quantas cópias desejar, desde que sejam para uso pessoal. É vetada a distribuição deste eBook,
mediante cópia ou qualquer outro meio de reprodução, para outras pessoas. Se você recebeu
este eBook através de e-mail ou via FTP de algum site da Internet, ou através de CD de Revista,
saiba que você esta com uma cópia pirata, não autorizada. Se for este o seu caso entre em
contato com o autor através do e-mail [email protected] ou comunique diretamente ao nosso
site através do e-mail [email protected].
Ao regularizar a sua cópia, você estará remunerando, mediante uma pequena quantia, o trabalho
do autor e incentivando que novos trabalhos sejam disponibilizados.
Visite periodicamente o site www.juliobattisti.com.br para ficar por dentro das novidades!
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
ii
Pré-requisitos Para completar este curso é necessário um conhecimento intermediário de VBA, funções de
planilha (tais como PROCV) e estar familiarizado com os controles básicos da caixa de
ferramentas do VBA tais como botão de comando (CommandButton), caixa de texto (TextBox) e
rótulo (Label). Embora boa parte do material envolva VBA mais avançado um grande esforço foi
feito para que mesmo com um conhecimento mínimo, o leitor possa tirar grande proveito do
material.
Como este curso não tem por objetivo ensinar qualquer outra coisa a não ser listbox e
combobox em formulários utilizando VBA, qualquer outro controle utilizado não terá prioridade
nas explicações. Entre os controles que aparecerão no decorrer deste módulo estão label
(rótulo), textbox (caixa de texto), CommandButton (botão de comando) e Frame (moldura). O
módulo vai do mais simples ao mais complexo estilo de listbox e combobox que pode ter
diversas utilidades em seu trabalho diário.
Como formulários não param somente aqui, este assunto precisou ser dividido em partes onde
controles similares serão discutidos em conjunto.
Os leitores interessados podem adquirir o curso básico de Excel em 120 lições no seguinte
endereço: www.juliobattisti.com.br/excel120/excel120.asp que servirá como trampolim
para um melhor aproveitamento e desenvolvimento deste módulo.
Este curso pode ser adquirido em conjunto com outros cursos do CD04. Para maiores
informações, visite www.juliobattisti.com.br ou envie um e-mail para
Série “Como Fazer”: Criando menus, barras de comando e botões personalizados no Excel
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
iii
Objetivos deste eBook Este eBook foi dividido em módulos. Este módulo visita a utilização de listbox e combobox em
formulário no Excel usando o Visual Basic for Application (VBA).
O trabalho foi desenvolvido a partir da demanda dos usuários do site www.juliobattisti.com.br. O
material procura analisar questões pertinentes ao dia-a-dia de seu trabalho. Vários exemplos são
retirados das dúvidas colocadas no fórum do site ou enviadas diretamente para o autor pelos
assinantes do site.
A linguagem utilizada é descontraída e com o mínimo de jargão possível. O objetivo é ter um
eBook com conteúdo relevante e de fácil compreensão.
Qualquer dúvida referente a este módulo podem ser colocadas diretamente no fórum Excel
avançado no endereço: http://www.juliobattisti.com.br/forum/default.asp
Comentários e sugestões para melhora do material podem ser enviados diretamente para o autor
no endereço [email protected]
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
iv
ÍNDICE ANALÍTICO
Introdução ........................................................................................................................................1 Bem-vindo a série “Como Fazer”. ...........................................................................................1 Antes de continuar ..................................................................................................................1
1. O que são listbox e combobox................................................................................................2
2. Visão geral dos controles........................................................................................................4
3. Adicionando itens....................................................................................................................7
4. Adicionando eventos.............................................................................................................12
5. Classificando itens em uma combobox e listbox ..................................................................22
6. Adicionando itens únicos ......................................................................................................27
7. Passando itens entre listboxes .............................................................................................31 7.1. Movendo itens dentro de listboxes...............................................................................34
8. Conectando e interagindo com o MS Outlook ......................................................................38
9. Conectando e interagindo com o MS Access .......................................................................45
10. Sobre o autor ........................................................................................................................60
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
1
SÉRIES: COMO FAZER
Formulários no Excel Utilizando VBA: Listbox e Combobox por Robert Friedrick Martim
Introdução
Bem-vindo a série “Como Fazer”.
Nas séries que serão escritas estaremos olhando aspectos distintos do Excel de acordo com a
demanda do fórum Excel Júlio Battisti (http://www.juliobattisti.com.br). A intenção principal é
fornecer ao internauta uma ferramenta que concentre a atenção na solução de um problema
específico.
Nesta série estaremos vendo a criação de diversos listbox e combobox. Iremos utilizar
métodos manuais e dinâmicos para criar e manipular estes controles. Estaremos olhando os
elementos que compõem estes dois controles e como podemos utilizá-los para nosso benefício de
forma dinâmica e eficiente.
Antes de continuar
O trabalho desenvolvido foi testado para compatibilidade com Excel 2002 e 2003. Devido à rápida
mudança em termos de tecnologia de software, atenção sempre será dada às versões mais
recentes do aplicativo Excel.
Não existe um pré-requisito per se; porém, o leitor deve estar ciente do que foi dito na parte de
pré-requisito no início deste módulo. Sem o devido conhecimento de algumas partes básicas este
módulo se tornará mais laborioso e difícil do que realmente é para aqueles sem o conhecimento
básico.
Sugestões serão sempre bem-vindas e esperamos que o leitor participe de forma proativa no
desenvolvimento do material aqui apresentado.
Finalmente, quando objetos e variáveis são dimensionados nesta apostila é utilizada a convenção
de dimensionamento dos objetos e variáveis. Por exemplo, um botão é dimensionado como Dim
btn.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
2
1. O que são listbox e combobox
Caixa de Combinação (ComboBox) e Caixa de Listagem (ListBox). Caixa de Combinação e
Caixa de Listagem são controles fornecidos através da "caixa de ferramentas de controle"
(Controls Toolbox) do Visual Basic for Application (VBA) disponível nos produtos
que compõem o Microsoft Office.
Caixa de listagem, como o nome sugere, é uma caixa contendo uma lista de itens. Estes itens
podem estar listados em uma ou mais colunas e conter diversas linhas, por exemplo. Dependendo
do tamanho da caixa de listagem vários itens podem ser mostrados simultaneamente. Caso os
itens excedam o tamanho da caixa, barras de rolagem são disponibilizadas para que o usuário
possa navegar pelos itens.
Caixa de combinação (combobox -também referido como dropdown list) mostra,
diferentemente da caixa de listagem, apenas um item por vez. Para acessar os itens da lista
precisamos “abrir” a lista, como mostra a figura abaixo:
Figura 1-1
Cada um dos controles possui os seus nomes na figura acima.
Nesta figura, podemos ver uma utilidade destes controles. Vamos supor que para cada item da
combobox existe uma lista. E para cada item da lista exista uma descrição. O que faremos é
construir o formulário de forma que quando um item for selecionado na combobox os itens da lista
mudem para refletir esta mudança. Da mesma forma, criaremos código para lidar com a seleção
de um item na listbox de forma que a label (rótulo) passe a descrição do item.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
3
Como o módulo não se preocupará com formatos e layout de formulário, o leitor deve estudar a
estrutura do formulário acima antes de continuar.
Para todos os formulários desenvolvidos será boa prática analisar a estrutura e códigos antes de
continuar para uma melhor compreensão.
O formulário acima pode ser acessado na planilha Form1.xls.
O trabalho que desenvolveremos a seguir será construído em cima deste primeiro formulário.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
4
2. Visão geral dos controles
Antes de nos aprofundarmos em combobox e listbox, precisamos passar por uma introdução
aos dois objetos (controles) que estaremos utilizando. Combobox e listbox são controles. Estes
dois controles possuem várias propriedades e métodos iguais; e cada um possui seus próprios
métodos e propriedades distintas. A figura abaixo mostra algumas destas propriedades:
Figura 2-1
Algumas propriedades podem ser consideradas mais importantes do que outras, porém, cada
uma desempenha um papel na programação. Veja, por exemplo, a propriedade BoundColumn.
Esta propriedade instrui o VBA a “amarrar” os dados a coluna um. Obviamente, ela não tem
nenhuma utilidade se temos apenas uma coluna (como na figura acima). Porém, ao modificarmos
a propriedade referente ao número de colunas (ColumnCount), ela passa a ter significado.
A propriedade name é outra de grande importância. Muitas vezes é fácil simplesmente aceitar o
nome sugerido; contudo, quando o número de controles aumenta se os nomes não têm um
significado além de ListBox ou Combobox, ficará difícil compreender o papel de cada um em
nosso código. Como convenção, o nome de uma listbox vem prefixada com lst e combobox
com cbo. O fato é que no formulário é óbvio quem é quem, isto é, o que é uma combobox e uma
listbox. Já no código, sem o prefixo, pode ser complicado saber quem é quem. Por exemplo, se
temos uma textbox, uma listbox e uma combobox em um formulário, sem o prefixo, e o
nome do objeto é teste. No código temos que teste.text = “teste”. Bom, sem o prefixo
precisamos ver quem é o tal teste, pois todos os três controles possuem a propriedade text. Se
ao invés tivéssemos txtTeste.text = “teste”, saberíamos que o controle é uma textbox.
Pode parecer um detalhe e querer ser pedante, mas somente apreciamos a importância destes
detalhes quando o volume de código cresce.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
5
A propriedade ColumnHeads é comumente utilizada em listboxes. Ela retorna o cabeçalho das
colunas, como mostra a figura:
Figura 2-2
Infelizmente, esta propriedade somente funciona com dados de um range na planilha. Quando os
dados são carregados através de loops ou métodos dinâmicos o cabeçalho fica em branco.
Portanto, se você pretende utilizar cabeçalhos em seu projeto tenha isso em mente.
Uma propriedade que aparece na Figura 2-1 e que pode causar confusão é a ControlSource.
ControlSource, diferentemente do que o nome pode sugerir, retorna o índice do valor
selecionado. Como a listbox é uma matriz cuja base é zero, o primeiro item selecionado na
matriz retorna um índice igual a zero. Ao anexarmos este índice a uma célula na planilha, esta
célula assume o índice atual selecionado.
Continuando a descer, a propriedade List tem o formato de uma matriz-tabela. Em outras
palavras, se temos um conjunto de dados dentro de uma Array (tabela) os valores podem ser
descarregados de uma só vez para esta propriedade.
A seguir temos a propriedade MultiSelect. Esta propriedade permite a múltipla seleção de
itens em uma listbox. Esta propriedade é útil quando desejamos passar itens de uma listbox
para outra (ou para uma localidade qualquer) com um clique apenas.
Logo abaixo de MultiSelect vem a propriedade RowSource. RowSource indica a fonte de
dados que preencherá a listbox ou combobox. RowSource pode receber como argumentos
um range, ie A1:E10, um “nome” referente a um range, ou uma referência a um range em uma
planilha qualquer.
RowSource funciona muito bem quando utilizamos nomes dinâmicos. Caso contrário, ficamos
presos ao tamanho da matriz que contém os dados.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
6
Além do formato básico, listbox e combobox podem possuir botões de opção e caixas de
seleção. A diferença entre os dois está na propriedade MultiSelect. Se a propriedade for para
seleção simples, o botão será de opção e se houver multi-seleção o botão será de seleção. Este
estilo pode ser modificado na propriedade ListStyle.
Figura 2-3
Na figura acima, na primeira listbox somente podemos selecionar um item por vez. Na segunda
listbox, podemos selecionar um ou mais itens por vez (A pasta de trabalho contendo este
modelo pode ser acessada em Form1.1.xls)
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
7
3. Adicionando itens
Há diversas formas de se adicionar itens a combobox e listbox. Estaremos vendo cada uma
destas formas separadamente. Quando as formas estão relacionadas, elas ficarão sob o mesmo
título do tópico. Quando a construção for completamente diferente, elas serão tratadas sob títulos
diferentes.
A maneira mais fácil de adicionar um item a uma combobox ou listbox é utilizar o método
AddItem:
Private Sub UserForm_Activate() cbo.AddItem "Adicionando itens a combobox" lst.AddItem " Adicionando itens a listbox " End Sub
Os itens acima são inseridos quando o UserForm é ativado (Activate). Quando o formulário é
carregado os itens são adicionados (este formulário está na pasta Form2.xls):
Figura 3-1
Podemos adicionar quantos itens forem necessários utilizando este método, porém, como o leitor
reconhecerá depois de algumas tentativas é que adicionar uma lista no código através deste
método pode representar um problema se a lista for muito grande.
Para solucionar este problema podemos utilizar a propriedade RowSource para carregar os itens
(este formulário está na pasta Form3.xls). Esta propriedade pode ser resolvida de duas formas:
a) diretamente na caixa de propriedade do controle que desejamos alocar a lista (ie listbox ou
combobox) e b) diretamente no código onde fazemos a referência ao controle. A figura abaixo
mostra como isso pode ser feito:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
8
Figura 3-2
Na figura acima, modificamos a propriedade RowSource do controle combobox para carregar os
itens contidos na planilha cboItens que se encontram nas células A1, A2 e A3 (no intervalo
A1:A3). Como listbox e combobox têm esta propriedade em comum, se desejamos criar uma
lista para a listbox, basta modificar a propriedade RowSource como feito acima.
A alternativa é utilizar uma linha de comando para preencher a lista:
Private Sub UserForm_Activate() Cbo.RowSource = "cboItens!A1:A3" End Sub
Independentemente do método utilizado o resultado é o mesmo:
Figura 3-3
Além do método AddItem e da propriedade RowSource, podemos utilizar a propriedade List
para obter o mesmo resultado. A propriedade List recebe uma matriz contendo todos os itens.
Estes itens são, então, descarregados de uma só vez para o controle. Novamente, tanto a
listbox quando a combobox compartilham esta propriedade e ambos são, portanto, carregados
da mesma forma.
Para que esse método seja viável precisamos construir a matriz contendo os dados. O exemplo a
seguir mostra como isso pode ser feito:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
9
Private Sub UserForm_Activate() Dim ws As Worksheet Dim matriz() Set ws = ThisWorkbook.Sheets("lstItens") últimaLinha = ws.Range("A65536").End(xlUp).Row ReDim matriz(últimaLinha) With ws For i = 0 To últimaLinha - 1 matriz(i) = .Cells(i + 1, 1) Next End With lst.List = matriz End Sub
Primeiramente, precisamos dizer ao programa onde os dados estão. Assim como no RowSource
dizemos que os dados estão na planilha cboItens, aqui definimos a planilha como sendo
lstItens. Se isso não for feito o programa carregará as linhas da planilha que estiver ativa
quando chamamos o formulário.
A definição da matriz é deixada em aberto, isto é matriz(), porque não sabemos quantos itens
serão carregados. Após descobrimos qual a última linha (últimaLinha =
ws.Range("A65536").End(xlUp).Row) redimensionamos a matriz (ReDim
matriz(últimaLinha)).
A partir daí criamos o loop que preencherá a matriz com as informações que desejamos e
finalmente preenchemos a listbox (lst.List = matriz).
O processo pode parecer complicado, mas não é. Na verdade, o processo representa uma grande
vantagem sobre o RowSource ou AddItem. Observe que se a lista aumentar ou diminuir,
precisamos modificar a propriedade RowSource para levar isso em conta. Já com o método
AddItem precisamos remover/adicionar diretamente no código. Contudo, o método utilizando a
matriz não apresenta este problema.
Se uma linha é adicionada ou removida, não importa. Ao localizar a última linha não vazia, sempre
teremos o número correto de itens em nossa combobox ou listbox no redimensionamento da
matriz.
Além disso, podemos preencher a listbox e combobox simultaneamente, bastando apenas
criar uma matriz para a combobox e uma para listbox.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
10
Os itens carregados por este método:
Figura 3-4
Se a criação do código é uma dor de cabeça para você, ainda há uma solução através de
fórmulas da planilha combinada com RowSource.
Para isso, precisamos criar um “nome” dinâmico para a área que representará nosso RowSource.
Utilizaremos uma combinação das funções Desloc e Cont.Valores para criar esta fórmula
mágica. Vamos supor que o RowSource esteja na planilha cboItens na coluna A. Selecione uma
célula qualquer na coluna A e vá até Nomes Definir. Dê um nome qualquer à sua área de
dados e para a área contendo os dados entre a seguinte fórmula:
=DESLOC(cboItens!$A$1,0,0,CONT.VALORES(cboItens!$A:$A),1)
A figura abaixo mostra como isso é feito:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
11
Figura 3-5
Observe que não desejamos um deslocamento lateral, apenas vertical. A função
Cont.Valores() define este tamanho vertical. No último argumento da função podemos definir
a largura da matriz retornada pela função DESLOC. Por exemplo, se desejamos uma matriz com
quatro colunas, basta modificar o número 1 para 41.
Agora, precisamos modificar o código. Na linha referente ao RowSource o definimos como:
Private Sub UserForm_Activate() Cbo.RowSource = "cbotItem" End Sub
Com a utilização das funções Desloc e Cont.Valores quando itens são acrescentados o nome
é automaticamente atualizado para incluir ou excluir valores na coluna A. Se o usuário acrescenta
um item ele é adicionado ao RowSource e se um item é removido no “nome” este item é removido
do RowSource.
A beleza deste método é que não mais precisamos nos preocupar com o RowSource e o código
fica bem mais leve com uma linha de código apenas.
Este exemplo encontra-se na pasta de trabalho Form3.xls.
Partimos, agora, para a criação de eventos.
1 Ao modificar o número de colunas no “nome”, não esquecer de modificar a propriedade ColumnCount para o número de colunas desejadas.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
12
4. Adicionando eventos
Até agora vimos o que são e como preencher estes dois controles. Nesta parte estamos
interessados em controlar os eventos destes controles. Os códigos desenvolvidos nesta parte
podem ser acessados na pasta de trabalho Form4.xls. Esta pasta de trabalho contém 3
planilhas, cujas guias são mostradas abaixo:
Figura 4-1
A intenção é utilizar estas guias para preencher a combobox. Para fazer isso é bem simples:
Private Sub UserForm_Activate() Dim ws As Worksheet Dim wb As Workbook Set wb = ThisWorkbook For Each ws In wb.Sheets cbo.AddItem ws.Name Next End Sub
Após o loop os itens são adicionados à combobox:
Figura 4-2
A combobox é carregada quando o evento Activate do formulário ocorre. Como desejamos que
a listbox seja preenchida conforme selecionamos um item em nossa combobox, precisamos
utilizar o evento Change do combobox para fazer isso.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
13
Em cada planilha desta pasta de trabalho há itens para a listbox e a descrição do item, em
suas respectivas planilhas. Como cada planilha contém os itens e respectivas descrições e cada
planilha é o nome na combobox, fica relativamente fácil resolver este problema através do evento
Change:
Private Sub cbo_Change() Dim ws As Worksheet Dim wb As Workbook Dim matriz() Set wb = ThisWorkbook Set ws = wb.Sheets(cbo.Text) 'limpa a lista anterior antes de adicionar uma nova lst.Clear 'encontra a última linha não-vazia na coluna A últimaLinha = ws.Range("A65536").End(xlUp).Row n = últimaLinha - 1 ReDim matriz(n) With ws 'vamos até o "n - 1" porque a primeiro item da matriz é 0 For i = 0 To n - 1 matriz(i) = .Cells(i + 2, 1) & " da planilha " & ws.Name Next End With lst.List = matriz End Sub
A matriz é preenchida iniciando-se na linha i+2, pois a primeira linha contém o cabeçalho dos
itens e das descrições. Caso contrário, o cabeçalho será incluído na matriz.
Quando um item é selecionado na combobox os respectivos itens da listbox são preenchidos:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
14
Figura 4-3
A mesma lógica segue para a descrição dos itens. Quando um item é selecionado na listbox o
rótulo mostra a descrição do item. Portanto, o nosso código no evento Click da listbox fica:
Private Sub lst_Click() Dim ws As Worksheet Dim wb As Workbook Set wb = ThisWorkbook Set ws = wb.Sheets(cbo.Text) lbl.Caption = ws.Cells(lst.ListIndex + 2, 2) _ & " da planilha " & cbo.Text End Sub
O código neste caso é bem mais simples do que o anterior. Apenas definimos em qual planilha
encontram-se as informações da lista e depois passamos o valor da descrição para o rótulo.
Como o ListIndex inicia-se em 0 (zero) e as informações iniciam-se na segunda linha,
precisamos ajustar isso. As descrições encontram-se na coluna 2 de cada planilha.
Ao clicar em um item qualquer em nossa lista a respectiva descrição é apresentada no rótulo,
como mostra a figura:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
15
Figura 4-4
Este exemplo mostra como passar o valor em um célula da planilha para um rótulo (label).
Contudo, esta mesma lógica pode ser aplicada para preencher textbox, por exemplo.
Vamos supor que tenhamos uma lista de clientes em uma planilha. Esta planilha contém os
nomes dos clientes e dados pessoais como endereço, telefone, fax, CPF, etc. Queremos
selecionar um nome em uma combobox e todos os detalhes serem preenchidos em textboxes
no formulário.
O nosso formulário terá a seguinte aparência (este formulário pode ser acessado na pasta de
trabalho Form5.xls):
Figura 4-5
Neste exemplo, estarei utilizando fórmulas, ao invés de código, para preencher os valores das
textboxes. Os valores para a combobox são carregados utilizando um “nome” como foi
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
16
mostrado anteriormente. Porém, a nossa fórmula para o nome mudará, pois neste caso nós temos
um cabeçalho o qual não queremos em nossa combobox. O “nome” deve se construído desta
forma:
=DESLOC(Clientes!$A$2,0,0,CONT.VALORES(Clientes!$A:$A)-1)
Neste caso estamos iniciando na segunda célula (A2) e subtraindo 1 (um) dos valores contados.
Ao subtrair 1, estamos removendo o cabeçalho, pois a contagem total inclui todos os valores na
coluna A.
Portanto, o código que será executado quando o formulário é aberto será2:
Private Sub UserForm_Initialize() cboNome.RowSource = "Clientes" cboNome.ListIndex = 0 End Sub
A linha referente ao ListIndex força a seleção do primeiro item da lista, isto é, o nome do cliente
cujo índice é zero:
Figura 4-6
Caso o leitor não queira ter nenhum nome selecionado, basta remover a linha de código referente
ao ListIndex ou passar o valor para –1 (este valor refere-se ao valor que não existe na lista).
O nosso próximo passo é preencher as textboxes conforme nomes sejam selecionados na
combobox. Novamente, utilizaremos o evento Change para isso. Contudo, ao invés de utilizarmos
código, utilizaremos a função PROCV para fazer isso. Em VBA a funções PROCV é VLOOKUP.
2 O nome “Clientes” pode ser entrado diretamente na caixa de propriedades da combobox, bastando apenas digitar o nome na caixa de propriedade, isto é digitar “Clientes” (sem as aspas) para a propriedade RowSource.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
17
O código a ser executado após o evento Change é:
Private Sub cboNome_Change() txtEndereco = WorksheetFunction.Vlookup _ (cboNome.Text, Range("A2:D100"), 2, False) txtTelefone = WorksheetFunction.Vlookup _ (cboNome.Text, Range("A2:D100"), 3, False) txtEmail = WorksheetFunction.Vlookup _ (cboNome.Text, Range("A2:D100"), 4, False) End Sub
O texto da combobox é o valor procurado, o intervalo A2:D100 é a área onde a busca ocorrerá, o
valor seguinte refere-se a coluna onde o valor deve ser procurado e o último item diz que o valor
procurado deve ser exato. Aqui, preferi escrever False. Não obstante, False tem o valor
numérico 0 (zero) . Quando fórmulas são grandes é preferível utilizar o valor numérico ao valor
literal.
Os valores para as textboxes são os valores encontrados. Ao selecionar um cliente diferente na
lista, os dados são automaticamente preenchidos:
Figura 4-7
Para o botão atualizar, encontramos um pequeno problema. Se utilizarmos o ListIndex da
combobox para achar a linha onde os dados se encontram, iremos “corrigir” os dados para o
cliente errado. O que ocorre é que quando modificamos o valor da combobox, como este valor
não se encontra na lista, o valor da combobox passa para –1 (ListIndex = – 1). Ou seja,
precisamos encontrar uma outra solução.
A solução é criar um índice para os clientes. Neste exemplo, há um índice na coluna E (veja a
pasta de trabalho referente a este exemplo). Porém, para o índice também temos um pequeno
problema: e se o número for repetido? Se o número for repetido, temos mais uma dor de cabeça.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
18
Para resolver isso, temos que criar uma validação nas células que receberão os índices para
evitar a repetição dos índices. No exemplo, o número de cliente foi limitado a 99. Portanto, para
criar a validação dos dados selecione a área que vai de E2:E100 e entre a fórmula conforme
mostra a figura:
Figura 4-8
O que a fórmula faz é contar todos os valores no intervalo E2:E100 que sejam iguais a célula
atual (na figura, a célula atual é a E2). Se o resultado for igual a 1, o usuário pode continuar. Caso
contrário, ele precisa entrar o valor novamente.
Feito isso, estamos prontos para criar o código que atualizará os nossos dados. Primeiramente,
crie mais uma textbox no formulário (esta textbox está para visible = false, neste
exemplo). Veja a figura abaixo:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
19
Figura 4-9
Com a textbox, no evento Change da combobox, rearrumamos o código para levar em
consideração este novo controle:
Private Sub cboNome_Change() txtEndereco = WorksheetFunction.Vlookup _ (cboNome.Text, Range("A2:E100"), 2, False) txtTelefone = WorksheetFunction.Vlookup _ (cboNome.Text, Range("A2:E100"), 3, False) txtEmail = WorksheetFunction.Vlookup _ (cboNome.Text, Range("A2:E100"), 4, False) txtíndice= WorksheetFunction.Vlookup _ (cboNome.Text, Range("A2:E100"), 5, False) End Sub
Como o texto da textbox conterá o valor do índice e como sabemos que os nomes estão em
uma linha a mais do que o índice (o índice inicia-se em 1). Isto é, para índice igual a um o cliente
está na linha “índice +1”. Assim sendo, o código para o botão de atualização fica:
Private Sub cmdAtualizar_Click() Dim ws As Worksheet Set ws = ThisWorkbook.Sheets("Clientes") linha = txtíndice + 1 With ws .Cells(linha, 1) = cboNome .Cells(linha, 2) = txtEndereco .Cells(linha, 3) = txtTelefone .Cells(linha, 4) = txtEmail End With cboNome.RowSource = "Clientes" cboNome.ListIndex = txtíndice - 1 End Sub
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
20
Primeiramente, definimos a planilha onde o código deve ser atualizado através do Set. A seguir,
definimos a linha como sendo o txtíndice + 1. Com a planilha (ws) atualizamos os dados de
acordo com as informações contidas nos textboxes.
O próximo passo é atualizar o RowSource e finalmente definir o cliente a ser selecionado como
sendo o índice – 1, pois o ListIndex inicia-se em 1. Desta forma, o cliente com índice igual a
1 é, na verdade, o cliente 0 (zero) na combobox.
A figura abaixo mostra a atualização sendo feita:
Figura 4-10
Os valores circundados no userform são os novos valores (antes de se pressionar o botão
Atualizar). Os valores circundados na planilha são os valores antigos. Após a atualização, temos:
Figura 4-11
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
21
O índice, contido na coluna E, não é mostrado na figura por falta de espaço, porém, ele é
mostrado na textbox. Na pasta contendo este exemplo, este controle está para visible =
false. O índice, aqui, funciona de uma forma similar à chave-primária de um banco de dados.
Porém, a eficiência e confiabilidade deste método são muito mais limitadas.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
22
5. Classificando itens em uma combobox e listbox
Um problema encontrado por todos aqueles que utilizam listbox e combobox é ordenação,
alfabética ou numérica, dos itens que serão adicionados aos dois controles.
Uma solução bastante óbvia é gravar uma macro que coloque os itens na ordem que desejamos e
depois criar um loop para carregá-los. Ainda na mesma lógica, seria copiar todos os itens, jogá-
los em uma planilha temporária, ordená-los, passá-los para o controle e limpar a planilha
temporária.
É desnecessário dizer que após algumas tentativas com erros e acertos, chegaremos a conclusão
que o método não é muito eficiente, embora ele resolva o nosso problema.
Para aqueles que leram o meu tutorial sobre este mesmo assunto, eles devem entender o porquê
da conclusão do tutorial. Lá foram apresentadas formas de se preencher estes controles e aqui
existem formas mais eficientes e completamente diferentes das apresentadas no tutorial. Se você
não possui o tutorial ele pode ser baixado gratuitamente em
http://www.juliobattisti.com.br/artigos/colunas/Robert/coluna01.asp
Primeiramente, não estaremos interessados em ordenar os itens diretamente nos controles.
Iremos, porém, analisar como isso é feito. Faça uma busca no Ajuda do VBA por ASCII. Na lista,
veremos como os itens são tratados em ordem crescente. Na lista, veremos que A < B < C... Os
quais são menores que a < b < c...
Uma ordenação segue esta tabela. Portanto, uma classificação do maior para o menor analisará
os itens de trás para frente e vice versa, pois ou vamos a uma direção ou noutra. Este é o nosso
primeiro passo para a compreensão de como a ordenação funciona.
O segundo requer entender como o Excel manipulará os dados conforme eles são ordenados.
É desnecessário dizer que o Excel é uma grande matriz. Como tal, tudo que é manipulado é
jogado em uma matriz. Como não sabemos de antemão o tamanho desta matriz, precisamos
deixar a parte superior da matriz (UBound) em aberto e calcular este valor em tempo de
execução.
Aqui entra em cena a propriedades List. Como visto anteriormente, esta propriedade tem o
formato de uma matriz e os dados que ela recebe devem vir de uma matriz também. Como a
propriedade é chamada de List, estaremos chamando a matriz que conterá os itens de List,
também.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
23
Iniciamos, então, a construção de nossa função:
Function Ordenar(Lista As Range) As Variant Dim List() n = Lista.Count ReDim List(n - 1) End Function
A nossa função é Variant porque não sabemos as dimensões que ela tomará ao resolver o
problema. A lista é um range que virá de nossa planilha. A princípio a List é aberta pois não
temos o tamanho da lista. Ao definirmos n como sendo o número de itens contido na lista,
redimensionamos a List como sendo n – 1. Como a base é Option Base 0, o primeiro item
da matriz é 0 (zero). Se não subtrairmos 1 de n, a matriz conterá um item a mais do que o range.
No próximo passo, preenchemos a lista (List):
Function Ordenar(Lista As Range) As Variant i = 0 For Each Item In Lista List(i) = Item 'Debug.Print Item i = i + 1 Next End Function
O Debug.Print Item serve para jogar cada Item na janela imediata. Utilizei este método de
depuração para visualizar os dados sendo carregados para a matriz. Com a List pronta,
podemos iniciar o processo de ordenação das variáveis contidas na lista:
Function Ordenar(Lista As Range) As Variant For i = 0 To UBound(List) - 1 For j = i + 1 To UBound(List) If List(i) > List(j) Then Temp = List(j) List(j) = List(i) List(i) = Temp End If Next j Next i End Function
Primeiramente, definimos os loops. Como não sabemos o limite superior da matriz3, utilizamos a
função UBound(matriz) para descobrir qual o último valor da lista. A matriz inicia-se em 0
(zero), pois o estamos utilizando Option Base 0. Se você deseja ser pedante, pode-se utilizar
LBound(Matriz) para achar o limite inferior da matriz, o qual retornará zero.
3 Na verdade, nós sabemos, pois a matriz é redimensionada como sendo n – 1. Porém, é sempre boa idéia utilizar este método para evitar erros.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
24
A seguir testamos (utilizando o formato da tabela ASCII), se o valor i é maior do que o valor i +
1 (j), pois queremos uma lista em ordem crescente. Se a lista for em ordem decrescente, basta
trocar o sinal de maior (>) pelo sinal de menor (<).
Finalmente, definimos a nossa função como sendo igual a List. Contudo, ao construir a lista, a
matriz é transposta, pois os itens são avaliados na vertical e colocados lado a lado (horizontal).
Assim sendo, precisamos devolver a matriz para o formato original. O código final fica, portanto:
Function Ordenar(Lista As Range) As Variant Dim List() n = Lista.Count ReDim List(n - 1) i = 0 For Each Item In Lista List(i) = Item 'Debug.Print Item i = i + 1 Next For i = 0 To UBound(List) - 1 For j = i + 1 To UBound(List) If List(i) > List(j) Then Temp = List(j) List(j) = List(i) List(i) = Temp End If Next j Next i Ordenar = WorksheetFunction.Transpose(List) End Function
A matriz List poderia ser transposta em um loop. Não obstante, a função Transpose faz a
mesma coisa com muito mais eficiência.
Como estamos falando de uma função, ela pode ser colocada em um planilha para checarmos os
resultados. Como estamos falando de uma matriz-tabela é importante selecionar a área que
receberá o resultado e apertar CTRL+SHIFT+ENTER após entrar a fórmula:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
25
Figura 5-1
Este primeiro exemplo é mostrado para que o leitor entenda o que está ocorrendo. Para adicionar
os itens a uma listbox, por exemplo, fica muito simples.
O arquivo Form 5.1.xls contém o formulário abaixo:
Figura 5-2
Como foi observado na lista ASCII, R < r; portanto, se você ordenar os nomes robert1 e
ROBERT2 em ordem crescente ROBERT2 virá antes de robert1. Em ordem alfabética crescente,
seria ao contrário, pois estaríamos ignorando maiúsculo/minúsculo. Portanto, sem ter a lista em
mãos, você não entenderá a lógica por trás da ordenação.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
26
Se você achou a parte de ordenação difícil demais. Para preencher a lista, você achará
ridiculamente fácil:
Private Sub UserForm_Activate() ListBox1.List = Ordenar(Range("A2:A21")) End Sub
Como a ordenação requer matrizes, a operação fica complexa pelo fato de não podermos
visualizar a matriz. A melhor saída é utilizar o Debug.Print para resolver isso.
Finalmente, a escolha por uma função ao invés de uma sub-rotina foi apenas para mostrar como
ela pode ser utilizada na planilha e para visualização do resultado antes de passá-lo para a
listbox. Não há nada que impeça a utilização de uma sub-rotina para retornar a mesma matriz.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
27
6. Adicionando itens únicos
Já passamos pela parte onde adicionamos itens ao combobox/listbox e classificamos os itens.
Porém, há situações especiais onde queremos que os valores sejam únicos.
Vamos supor que no exemplo anterior, além dos dados já cadastrados também tenhamos a
Unidade Federativa (UF) de cada cliente. É fácil ver que este valor se repetirá na coluna referente
a UF. Estão-se passando este valor para uma textbox não há problemas, pois é isso mesmo que
desejamos fazer. Contudo, estaremos analisando o mesmo problema de uma ótica diferente.
Estaremos vendo como preencher uma combobox com valores únicos onde várias cidades sob a
mesma UF são colocadas em uma listbox a partir da UF selecionada.
Valores únicos podem ser adicionados de duas formas: 1) através de fórmulas ou 2) uma função
customizada (personalizada) pelo usuário. Em ambos os casos, porém, o resultado é uma matriz
contendo todos os itens únicos. Primeiramente, avaliamos uma função que retorna uma matriz
contendo todos os valores únicos. Esta matriz, como na caso da classificação, é jogada de uma
só vez para a propriedade List do controle.
Para criarmos uma lista única utilizaremos uma coleção (Collection). Ao utilizar uma nova
coleção (New Collection), podemos associar um item da lista a uma chave, evitando assim a
repetição do item.
Os modelos aqui desenvolvidos encontram-se na pasta de trabalho Form 6.2.xls.
Como sempre, iniciamos com a declaração das variáveis:
Private Function matriz(lista As Range) As Variant Dim matrizSaída() As Variant Dim Item As Variant Dim matrizÚnica As New Collection End Function
Estaremos utilizando, primeiramente, uma função para fazer o que desejamos. A matriz de saída
é deixada em aberto porque desconhecemos o tamanho da lista. Uma vez que a lista tenha sido
passada para a função, preenchemos o nova coleção de dados:.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
28
Private Function matriz(lista As Range) As Variant On Error Resume Next For Each Item In lista If Item.Formula <> "" Then matrizÚnica.Add Item.Value, CStr(Item.Value) End If Next Item matriz = "" End Function
Aqui, acrescentamos os itens a nova coleção de dados (matrizÚnica). A chave (similar a chave-
primária de um BD) é dada como sendo a String do valor do Item atual. Observe que se a
chave for igual ocorrerá um erro. Para evitar isso, utilizamos o On Error Resume Next (No erro
executar próximo comando). Ao executar o próximo comando o item onde o erro ocorreu é pulado
e somente os itens que não retornam um erro são adicionados a nova coleção. A última linha
apenas define a matriz como sendo vazia.
Private Function matriz(lista As Range) As Variant If matrizÚnica.Count > 0 Then ReDim matrizSaída(1 To matrizÚnica.Count) For i = 1 To matrizÚnica.Count matrizSaída(i) = matrizÚnica(i) Next i matriz = matrizSaída End If End Function
Finalmente, checamos se o número de itens da coleção é maior do que zero. Se for, redimensiona
a matriz de saída. Aqui, utilizo um forma diferente de se declarar o intervalo da matriz. Como
Option Base é zero, teríamos que subtrair 1 do número total de itens. Ao dimensionar a matriz
com sendo de 1 ao número total (1 To matrizÚnica.Count) não há necessidade de subtração
é a dimensão é explícita, pois sabemos o limite inferior (LBound) e limite superior (UBound).
A função completa:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
29
Private Function matriz(lista As Range) As Variant Dim matrizSaída() As Variant Dim Item As Variant Dim matrizÚnica As New Collection On Error Resume Next For Each Item In lista If Item.Formula <> "" Then matrizÚnica.Add Item.Value, CStr(Item.Value) End If Next Item matriz = "" If matrizÚnica.Count > 0 Then ReDim matrizSaída(1 To matrizÚnica.Count) For i = 1 To matrizÚnica.Count matrizSaída(i) = matrizÚnica(i) Next i matriz = matrizSaída End If End Function
O nosso próximo passo e preencher a combobox.
Private Sub UserForm_Initialize() Linha = Range("A65536").End(xlUp).Row Dim valores As Variant Dim i As Long valores = matriz(Range("A2:A" & Linha)) With cbo1 For i = 1 To UBound(valores) .AddItem valores(i) Next End With cbo1.ListIndex = 0 End Sub
Primeiramente, procuramos pela última linha na coluna A. Em seguida definimos a variável
valores como sendo o resultado da matriz anterior e finalmente damos um loop em cada valor
e preenchemos a combobox. O primeiro item da combobox que é selecionado é aquele cujo
ListIndex é zero.
Aperte o “pause” do VBA e pense um pouco... Será que não há nada de estranho neste código?
Para que criar uma matriz chamada valores e dizer que essa matriz é igual a função? Pior ainda,
para que fazer um loop quando temos em mão a matriz completa!
O código funciona bem, mas estamos repetindo o trabalho já feito pela função.
Como a função matriz resolvida, podemos facilmente preencher a combobox, com a seguinte
sub-rotina:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
30
Private Sub UserForm_Initialize() Linha = Range("A65536").End(xlUp).Row cbo1.List = matriz(Range("A2:A" & Linha)) cbo1.ListIndex = 0 End Sub
Com apenas três linhas resolvemos o problema!
Agora, dê um “rewind” até a função. Embora a função seja ideal (por retornar valores que podem
ser divididos com outros procedimentos), o mesmo resultado poderia ter sido obtido diretamente
no evento Initialize do formulário.
Como o processo é similar a criação da função é desnecessário repetir todo o código no papel.
Contudo, o material foi desenvolvido na pasta de trabalho e está disponível para o leitor.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
31
7. Passando itens entre listboxes
Uma característica interessante de listboxes é que podemos passar itens de uma lista para
outra. Em algum ponto, o usuário já deve ter tido esta experiência. Por exemplo, quando
utilizamos o Outlook para enviar e-mails, temos uma listbox e três textboxes. Uma contém a
lista de e-mail em nosso computador e a outra recebe os e-mails das pessoas para as quais
desejamos enviar a mensagem.
Por incrível que pareça, transferir itens entre listboxes é bem simples. Primeiramente, vamos
iniciar com a construção de nosso formulário. O formulário do usuário deve ter o formato a seguir:
Figura 7-1
A listbox da esquerda conterá a lista completa e a da direita receberá os itens. Além disso,
temos quatro botões de comando. O botão com duas setas para a direita insere na segunda
listbox todos os itens da primeira listbox. O botão com uma seta insere apenas o item
selecionado.
A mesma lógica serve para os botões de remover. Uma seta remove o item selecionado e duas
setas remove todos os itens. Então, vamos iniciar pela parte mais fácil: passar/remover todos os
itens da lista.
Entre no código do primeiro botão, onde entraremos o código:
Private Sub cmdAdicionarTodos_Click() On Error Resume Next lstRecebeItens.List = lstItens.List End Sub
Tudo que fazemos é definir a List da listbox da direita (lstRecebeItens) como sendo igual
a lista dos da primeira listbox. A linha On Error Resume Next apenas assegura que se
houver um erro o código continuará a rodar.
Se passar toda a lista foi simples, remover todos os itens da segunda lista é mais fácil ainda:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
32
Private Sub cmdRemoverTodos_Click() On Error Resume Next lstRecebeItens.Clear End Sub
Não precisamos da um loop em cada item da lista e remover um a um. Basta utilizar o método
Clear e resolvido o problema!
A nossa próxima parada é adicionar um item por vez, isto é, adicionar o item selecionado. Abra a
área de edição do código para o botão de adicionar o item selecionado. O nosso código, neste
caso, ficará:
Private Sub cmdAdicionarUm_Click() On Error Resume Next If lstItens.ListCount >= 1 Then If lstItens.ListIndex = -1 Then lstItens.ListIndex = _ lstItens.ListCount - 1 End If lstRecebeItens.AddItem (lstItens.Text) End If n = lstItens.ListIndex + 1 If n >= lstItens.ListCount Then
lstItens.ListIndex = 0 Else: lstItens.ListIndex = n End If End Sub
O código primeiramente checa se há algo na lista (lstItens.ListCount >= 1). Se sim, checa
o valor da seleção (lstItens.ListIndex = -1). Se o valor for -1, então o último item da lista
é selecionado e o texto deste item é passado para a segunda lista.
A seguir checamos qual o item atualmente selecionado. Após este item ser passado para a
segunda listbox, o item seguinte é selecionado. Se este for o último item da lista; então, o
primeiro item da lista é selecionado.
Para remover um item apenas é relativamente fácil. Tudo que precisamos saber é o índice do item
e utilizar o método RemoveItem para fazer isso:
Private Sub cmdRemoverUm_Click() On Error Resume Next If lstRecebeItens.ListCount >= 1 Then If lstRecebeItens.ListIndex = -1 Then lstRecebeItens.ListIndex = _ lstRecebeItens.ListCount - 1 End If lstRecebeItens.RemoveItem (lstRecebeItens.ListIndex) End If End Sub
Novamente checamos se há algum item na lista (lstRecebeItens.ListCount >= 1). Se
houver itens na lista, mas nenhum estiver selecionado, o último item da lista é removido. Se algum
item estiver selecionado, o item cujo índice está selecionado é removido.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
33
Figura 7-2
A imagem mostra um item sendo passado por vez. Após passar o Item 1, o segundo item da
primeira lista é automaticamente selecionado.
Além de passarmos um item por vez, podemos habilitar a multi-seleção para passar todos os itens
selecionados de uma só vez. Tanto o exercício anterior quanto este se encontram na pasta de
trabalho Form6.xls.
Antes de tudo precisamos modificar a propriedade da listbox para que ela aceite múltipla
seleção de itens. Na caixa de propriedade, modifique como segue:
Figura 7-3
A propriedade Multiselect é composta por três estados:
• frmMultiSelectSingle • frmMultiSelectMulti • frmMultiSelectExtended
O primeiro estado é padrão e permite apenas uma seleção por vez (como feito anteriormente). O
segundo, permite a seleção de vários itens através do clique do mouse, isto é, em cada item que o
usuário clicar ele será selecionado. O terceiro, o qual estaremos utilizando, o usuário precisa
pressionar e segurar a tecla CTRL enquanto clica em cada item para efetuar uma múltipla seleção.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
34
Não estaremos modificando o código para adicionar e remover todos os itens da lista
simultaneamente.
Para se passar um item selecionado, precisamos utilizar a propriedade Selected. Esta
propriedade não é opcional e, portanto, precisamos definir o item selecionado. Para passar os
itens selecionados, procederemos da seguinte forma:
Private Sub cmdAdicionarSel_Click() On Error Resume Next n = lstItens.ListCount - 1 If lstItens.ListCount >= 1 Then If lstItens.ListIndex = -1 Then lstItens.ListIndex = _ lstItens.ListCount - 1 End If For i = 0 To n If lstItens.Selected(i) = True Then lstRecebeItens.AddItem lstItens.List(i) End If Next End If End Sub
Primeiramente, contamos todos os itens da lista. Como estamos utilizando Option Base 0
(opção padrão para matrizes), o índice sempre é iniciado em zero. Assim sendo, o valor de n será
igual a lstItens.ListCount - 1. Novamente, checamos se há algo selecionado para depois
fazer um loop nos itens selecionados.
Durante o loop checamos se o item i está selecionado e se este for o caso, acrescentamos o item
i da primeira lista a segunda lista.
7.1. Movendo itens dentro de listboxes
Acima vimos como passar um ou mais itens entre duas listboxes. Agora, nos voltamos para a
passagem de itens dentro de uma listbox. Neste caso, o que estamos fazendo é mover a
posição atual do item.
O nosso formulário terá o seguinte aspecto:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
35
Figura 7-4
Com o nosso layout feito, estamos prontos para iniciar a nossa análise do problema.
Como já sabemos, a propriedade List define a matriz contendo os itens de nossa lista. Embora os
itens tenham sido adicionados um a um, o resultado é uma matriz. Portanto, para fazer o que
desejamos precisaremos manipular e reconstruir a matriz a cada passo.
Ao utilizarmos o Option Base padrão (Option Base 0), temos que a propriedade ListIndex
= 0 para o Item 1, ListIndex = 1 para Item 2 e ListIndex = 2 para o Item 3.
Se construirmos uma matriz contendo os itens acima, ela terá o mesmo formato. Se capturarmos
o ListIndex e o texto do Item 1, temos: ListIndex = 0 e Text = Item 1. Portanto,
precisamos guardar estas duas variáveis para movimentar os itens na nova matriz.
Vamos chamar nossa matriz de List. Ela é redimensionada de acordo com o número de itens na
listbox. O texto é igual ao texto da posição atual em nossa nova lista. O Item 1 passa para a
posição do Item 2 da lista atual. A nossa lista tem o formato atual:
• Item 1 • Item 2 • Item 3
Portanto, o Item 1 passa a ser igual a ListIndex + 1 (Item 2). E nossa matriz, passa a ser
• Item 2 • Item 2 • Item 3
Como havíamos guardado o Item 1 em Text, o Item 1 passa para posição onde ListIndex + 1.
Isto é List(ListIndex + 1) e igual a Text. E a nova matriz fica:
• Item 2 • Item 1 • Item 3
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
36
Observe que o itens não moveram. O que fizemos foi escrever Item 2 na posição onde se
encontrava o Item 1. E depois, escrevemos Item 1 sobre o segundo Item 2 (pois ficamos com o
Item 2 repetidos duas vezes nas posições 0 e 1).
O código desenvolvido utiliza o Debug.Print para mostrar o processo durante a execução:
Figura 7-5
O problema é bastante simples. Talvez a parte mais difícil seja visualizar o processo conforme ele
ocorre. Com as explicações dadas, podemos partir para a escrita de nosso código:
Private Sub imgParaBaixo_Click() Dim List() If lstItens.ListIndex = lstItens.ListCount - 1 Then Exit Sub End If n = lstItens.ListCount ReDim List(n - 1) 'Guarda a matriz original na "List" For i = 0 To n - 1 List(i) = lstItens.List(i) Next 'Guarda o índice da seleção atual ItemNúm = lstItens.ListIndex 'Item temporário é igual ao item selecionado TempItem = List(ItemNúm) 'Item atual da lista passa ser o item seguinte List(ItemNúm) = List(ItemNúm + 1) 'Utilize o Debug.Print para ver a mudanca na matriz 'Debug.Print "Primeiro Debug na janela imediata:" 'For i = 0 To n - 1 'Debug.Print List(i) 'Next
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
37
'Aqui, temos dois itens repetidos. Um na posição nova ItemNúm - 1 'E outro na posição original ItemNúm 'Portanto, ItemNúm + 1 na nova lista é igual ao TempItem List(ItemNúm + 1) = TempItem 'Debug.Print vbCr & "Segundo Debug na janela imediata:" 'For i = 0 To n - 1 'Debug.Print List(i) 'Next 'Define a nova List da listbox como sendo a List lstItens.List = List 'Seleciona o item que está sendo movido. Como a posição original é 'ListIndex (ItemNúm) ao mover para baixo ele passa a ser ItemNúm + 1 lstItens.ListIndex = ItemNúm + 1 End Sub
Como utilizei uma imagem com a seta, o evento é baseado no “click” sobre a figura. Se o
movimento para baixo envolve uma soma, o inverso é verdadeiro para o movimento para cima.
Portanto, ao compreender como o método acima funciona, criar o movimento inverso é um
passeio no parque:
Private Sub imgParaCima_Click() Dim List() If lstItens.ListIndex = 0 Then Exit Sub End If n = lstItens.ListCount ReDim List(n - 1) For i = 0 To n - 1 List(i) = lstItens.List(i) Next ItemNum = lstItens.ListIndex TempItem = List(ItemNum) List(ItemNum) = List(ItemNum - 1) List(ItemNum - 1) = TempItem lstItens.List = List lstItens.ListIndex = ItemNum - 1 End Sub
A pasta de trabalho contendo este exemplo pode ser acessada em Form6.1.xls.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
38
8. Conectando e interagindo com o MS Outlook
Para os usuário do MS Office, há várias formas de se interagir com outros aplicativos deste
pacote. Neste tópico e no próximo estaremos vendo exatamente isso.
Neste primeiro tópico, estaremos vendo como carregar para uma listbox os e-mails e nomes
dos contatos contidos em seu Outlook. Além disso, como bônus, uma pasta de trabalho contendo
um pequeno aplicativo para envio de e-mail do Excel foi criado. Não estaremos discutindo os
detalhes de como o programa foi feito ou como configurar a sua máquina para envio de e-mails.
Afinal, nosso foco está nas listboxes e comboboxes. Porém, o código está aberto para análise
e uso pelo usuário.
O formato de nosso formulário será o seguinte:
Figura 8-1
A caixa da esquerda é uma listbox e as três caixas da direita são textboxes. Este layout foi
escolhido para manter um formato similar ao do Outlook 2002 (Outlook XP).
Como os botões “Para”, “Cc” e “BCc” passam os valores da listbox para as respectivas caixas
de texto, não estaremos reconstruindo estes botões neste tópico, pois eles já foram tratados
anteriormente.
Os objetivos deste exercício estão listados abaixo:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
39
1. Carregar o nome do contato e seu respectivo endereço de e-mail a partir da lista de
contatos do Outlook;
2. Passar da listbox somente o endereço de e-mail para a respectiva caixa de acordo com
o botão clicado;
3. Permitir que o usuário passe um item para o destinatário através de um duplo-clique sobre
o nome do contato;
A primeira parte requer uma rotina que seja capaz de ler os dados contidos na pasta de contatos
do Outlook e passe os valores para uma matriz. Como estamos interessados no nome e e-mail,
precisamos modificar as propriedades da listbox como segue:
1. Passar o valor da ColumnCount para 2 (duas colunas, uma para os nomes e outra para
os e-mails);
2. MultiSelect deve estar para frmMultiselectExtended para permitir múltipla
seleção de destinatários que serão passados para as respectivas caixas de texto;
Para se acessar os objetos do Outlook podemos ir no escuro ou utilizar a referência a biblioteca
do Outlook4. Embora a utilização da biblioteca do Outlook facilite a nossa vida, estaremos criando
o nosso código no escuro. O motivo por esta escolha é para evitar incompatibilidade entre
sistemas dos leitores. Como não temos o benefício da biblioteca, teremos que criar os objetos. Os
objetos que precisaremos neste caso são:
• olApp (O aplicativo Outlook) • olNameSpace (NameSpace referente ao Outlook) • olContatos (os contatos) • olListaEnd (Lista de endereços) • olItensEnd (Itens da lista de endereços – olListaEnd)
O prefixo “ol” é para identificar os objetos relacionados ao Outlook Application (olApp).
Como o código é relativamente extenso, é interessante utilizar Option Explicit5 para evitar
erro em nossas variáveis.
Primeiramente, vamos dimensionar os nossos objetos:
Private Sub UserForm_Initialize() Dim olApp As Object 'Aplicativo Dim olNameSpace As Object 'NameSpace6 Dim olContatos As Object 'Itens Dim olListaEnd As Object 'Lista de endereços
4 Pra se fazer uma referência aos objetos do Outlook vá até Ferramentas --> Referências e selecione Microsoft Outlook <versão> Object Library. 5 Para forçar Option Explicit em todos os trabalhos vá até Ferramentas --> Opções --> Editor e selecione “Requer Declaração de Variáveis”. 6 Namespace é um conjunto de nomes no qual todos os nomes são únicos.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
40
Dim olItensEnd As Object 'Itens da lista de endereços End Sub
Como não temos a biblioteca, todos os itens são tratados como objetos. Com os objetos,
dimensionados, precisamos criá-los para que o código possa fazer sua mágica. O primeiro objeto
a ser criado é o olApp (o código segue a ordem de desenvolvimento e os códigos anteriores não
serão repetidos):
Private Sub UserForm_Initialize() 'A declaração dos objetos entra aqui Set olApp = CreateObject("Outlook.Application") End Sub
Como o olApp pode ser qualquer objeto precisamos criar o objeto Outlook. Isto é feito como
mostrado acima. Como os objetos seguintes são dependentes do primeiro objeto, podemos
continuar com o Set dos objetos:
Private Sub UserForm_Initialize() 'O NameSpace é definido em cima do aplicativo Set olNameSpace = olApp.GetNamespace("MAPI") 'A lista é definida em cima do NameSpace 'nomeDaPasta refere-se ao nome da pasta AddressLists 'o nome pode ser modificado pelo índice da pasta. O índice para a 'pasta padrão é 1 Set olListaEnd = olNameSpace.AddressLists("nomeDaPasta") 'Os itens contidos na lista (Entries) são definidos em cima da lista Set olItensEnd = olListaEnd.AddressEntries End Sub
A lista de nossa listbox será carregada a partir de uma matriz (utilizaremos a propriedade List
para isso). Desta forma precisamos criar tal matriz. Como não sabemos o tamanho da matriz em
termos de linhas (sabemos que teremos 2 colunas, uma para o nome e outra para o e-mail),
precisamos dimensionar (Dim) e redimensionar (ReDim) a matriz:
Private Sub UserForm_Initialize() Dim matriz() n = olItensEnd.Count ReDim matriz(n, 2) 'Faz um "loop" em cada cadastro do AddressBook 'e adiciona os itens "Name" e "Address" à nossa matriz For i = 0 To n - 1 Set olContatos = olItensEnd.Item(i + 1) nome = olContatos.Name endEmail = olContatos.Address 'Acrescenta o item "nome" a linha "i" na coluna 1 (índice 0) matriz(i, 0) = nome 'Acrescenta o item "endEmail" a linha "i" na coluna 2 (índice 1) matriz(i, 1) = endEmail Next 'Carrega os valores na lista. Onde a propriedade "list" é uma matriz lstContatos.List = matriz End Sub
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
41
Uma vez carregada a matriz, nosso trabalho está quase pronto. Como criamos vários objetos na
memória de nosso computador, não é uma boa idéia deixá-los consumindo a nossa preciosa
capacidade de processamento. Para cada objeto criado, faremos o seguinte:
Private Sub UserForm_Initialize() Set nomeDoObjeto = Nothing End Sub
O processo acima deve ser feito para cada objeto criado.
O código completo fica, portanto:
Private Sub UserForm_Initialize() Dim olApp As Object 'Aplicativo Dim olNameSpace As Object 'NameSpace Dim olContatos As Object 'Itens Dim olListaEnd As Object 'Lista de endereços Dim olItensEnd As Object 'Item da lista de endereços Dim blnListaExiste As Boolean Dim matriz() Dim nome As String, endEmail As String, índiceListEnd As Integer Set olApp = CreateObject("Outlook.Application") Set olNameSpace = olApp.GetNamespace("MAPI") 'O índice 2 refere-se ao valor em meu PC. Modifique o índice para 1 'para utilizar o AddressBook padrão: Set olListaEnd = olNameSpace.AddressLists(2) Set olItensEnd = olListaEnd.AddressEntries n = olItensEnd.Count ReDim matriz(n, 2) For i = 0 To n - 1 Set olContatos = olItensEnd.Item(i + 1) nome = olContatos.Name endEmail = olContatos.Address matriz(i, 0) = nome matriz(i, 1) = endEmail Next lstContatos.List = matriz Set olContatos = Nothing Set olListaEnd = Nothing Set olItensEnd = Nothing Set olNameSpace = Nothing Set olApp = Nothing End Sub
O nosso formulário, após rodarmos o código, carrega os dados de todos os contatos em nosso
AddressBook:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
42
Figura 8-2
Para evitar problemas com a minha lista de e-mails, foi necessário obliterar os detalhes.
O código final utilizado neste exemplo contem rotinas para lidar com erros e dá a flexibilidade de
se escolher o AddressBook a ser utilizado.
Esta pasta de trabalho contém um outro formulário que permite o usuário escrever e enviar um e-
mail. Este aplicativo utiliza o IIS (Internet Information Services) com um servidor SMTP virtual. O
aplicativo pode ser adaptado para enviar e-mail via Outlook. Contudo, ao enviar pelo Outlook
precisamos permissão para cada mensagem enviada. A utilização do servidor SMTP virtual
resolve o DNS (Domain Name Server) e envia a mensagem sem a necessidade do “prompt” do
Outlook.
Se você tem algum dúvida sobre como instalar e configurar o IIS, uma boa pedida é o livro
Windows Server 2003 – Curso Completo de Júlio Battisti, capítulos 22, 23 e 24. Para os usuários
de Windows XP Professional, veja o livro Windows XP Home & Professional, também de Júlio
Battisti.
O aplicativo (se é que podemos chamá-lo disso) para envio de e-mail é mostrado abaixo:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
43
Figura 8-3
Ele não é nenhuma Brastemp, mas quando estamos trabalhando com diversas planilhas e
precisamos enviá-las sem a chata mensagem do Outlook é que apreciamos a versatilidade deste
método. O código é extremamente fácil e o aplicativo pode ser adaptado para enviar anexos
também.
Ao utilizar a biblioteca do Outlook é possível criar um aplicativo de e-mail bem profissional no
Excel; porém, este assunto vai além do escopo deste módulo.
A aplicativo somente funciona se o IIS estiver instalado e o servidor virtual SMTP estiver
resolvendo DNS corretamente.
Uma última palavra sobre o envio de e-mails utilizando um servidor SMTP é que existe um
diferença entre o método utilizado no WinXP Pro e em um servidor Windows.
O WinXP Pro utiliza CDO.Message para criar a mensagem e servidor Windows 2000 utiliza
CDONTS. Já para o servidor Windows 2003, CDOSYS é o método utilizado para criar o objeto.
Neste dois últimos casos é necessário referenciar o servidor para que a mensagem seja criada.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
44
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
45
9. Conectando e interagindo com o MS Access
Para aqueles que participam do fórum Júlio Battisti (www.juliobattisti.com.br/forum/default.asp),
todos já sabem o que eu penso: Excel não é banco de dados. Se você possui informações que
precisam de um armazenamento mais avançado dos dados, utilize um Bando de Dados. Se você
trabalha com o Office, utilize o Access. Afinal, o Excel é para análise de dados e não para a coleta
de dados.
Contudo sempre existe aquela pergunta sobre como utilizar o Excel para acessar dados em um
BD. Há várias formas de se fazer isso. A mais simples é criar uma consulta que traz os dados
para um planilha do Excel. Feito isso, podemos manipular estas informações e fazer nossas
análises.
Não obstante, a consulta é passiva. Vamos supor que desejamos ler e escrever para o banco de
dados. Uma consulta não resolve este problema. Nesta parte, estaremos vendo exatamente isso,
isto é, como coletar informações de uma forma ativa em nosso banco de dados de forma que
possamos modificar ou acrescentar informações diretamente no BD. Obviamente, não temos
como modificar a estrutura do BD, mas com esta flexibilidade, podemos acrescentar mais um item
importante em nossa busca por um entendimento melhor de como estes programas interagem.
Embora o Excel venha com as classes que utilizaremos para construir a conexão ao BD do
Access, elas não são automaticamente referenciadas. Estaremos utilizando a biblioteca ADO
neste caso. Para referenciar a esta biblioteca, vá até (no VBE) Ferramentas --> Referências e
selecione a versão mais recente do Microsoft ActiveX Data Objects Library:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
46
Figura 9-1
Uma vez que a referência esteja criada, estamos prontos para iniciar o nosso trabalho. Os nossos
objetivos estão relacionados abaixo:
• Conectar ao BD
• Extrair os dados de uma tabela qualquer
• Passar os dados de um dos campos da tabela para uma combobox.
• Ao selecionar um dos registros na combobox, passar os resultados para textboxes em
nosso formulário
Este é o primeiro exercício que estaremos fazendo. Nele estamos apenas preocupados com a
leitura dos dados. Mais adiante veremos como modificar estas informações no banco de dados.
Como sempre iniciamos pela declaração de nossas variáveis. Estaremos precisando do seguinte:
• Conexão ao Banco de Dados (o qual chamaremos de conn)
• Recordset (registros, os quais chamaremos de rs)
• Um contador (para contar os registros, linhas, colunas, etc.)
Após a conexão ao banco de dados, o formulário terá o seguinte aspecto:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
47
Figura 9-2
Os dados de cada textbox são modificados conforme escolhemos um funcionário novo.
Quando conectamos a banco de dados, se o volume é grande o desempenho da conexão cairá.
Para tentar reduzir o problema, carregaremos o formulário antes de ele ser mostrado. Ao fechar,
ao invés de descarregar o formulário, simplesmente o esconderemos. Portanto, o primeiro código
a ser escrito deve ser na pasta de trabalho:
Private Sub Workbook_Open() Load frmDB End Sub
Os dados podem ser carregados através de uma função ou sub-rotina. A escolha fica a critério do
programador e não interfere com o resultado final. Estaremos utilizando uma sub-rotina para
resolver o nosso problema.
Sub carregarDados(nomeBD As String, Tabela As String) Dim conn As ADODB.Connection Dim rs As ADODB.Recordset End Sub
Sem a referência à biblioteca ADO, não temos como dimensionar os objetos Connection e
Recordset.
A nossa sub-rotina recebe dois argumentos (ambos textos) nomeDB e Tabela. O nomeDB refere-
se não só ao nome como também ao caminho (path) onde o banco de dados de encontra. O
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
48
banco de dados sendo utilizado está na pasta BD e é chamado FPNWIND.MDB7. Portanto, este
argumento será entrado como ThisWorkbook.Path & "\DB\FPNWIND.MDB".
Com os objetos dimensionados, passamos para o próximo item. Precisamos, agora, definir (Set)
os objetos.
Sub carregarDados(nomeBD As String, Tabela As String) Set conn = New ADODB.Connection conn.Open "Provider=Microsoft.Jet.OLEDB.4.0; Data Source=" & nomeBD & ";" Set rs = New ADODB.Recordset End Sub
Primeiro criamos uma nova conexão (New ADODB.Connection) e em seguida abrimos a conexão
utilizando o Driver apropriado e a fonte de dados (Data Source). Feito isso, criamos um rs
(Recorset) novo (New ADODB.Recordset). Assim como abrimos a conexão, precisamos agora
abrir o rs:
Sub carregarDados(nomeBD As String, Tabela As String) rs.Open "Select * FROM " & Tabela & " ORDER BY FirstName", conn sobrenome = "LastName": priNome = "FirstName" título = "TitleOfCourtesy" End Sub
Aqui, utilizamos comando SQL para abrir (ler) as informações. Ao abrir, nós selecionamos da
tabela (Select * From Tabela) e ordenamos pelo primeiro nome da pessoa (Order by
FirstName).
Observe que campos (LastName, FisrtName e TitleOfCourtesy) são os nomes dos campos
mesmo! Com isso quero dizer que este não é o cabeçalho do campo na tabela. Embora muitas
vezes estes sejam iguais, neste caso específico eles não são e é preciso entrar em modo de
edição da tabela no Access para saber o nome correto campo.
A seguir, é definido três variáveis que correspondem aos campos que nos interessam: sobrenome
(LastName), priNome (FirstName) e título (TitleOfCourtesy). Com estas variáveis,
passamos para o próximo estágio:
Sub carregarDados(nomeBD As String, Tabela As String) With rs If Not .BOF Then .MoveFirst While Not .EOF nomeCompleto = .Fields(título) & " " & .Fields(priNome) _ & " " & .Fields(sobrenome) frmDB.cboNome.AddItem nomeCompleto .MoveNext Wend End With
7 Este é um banco de dados gratuíto que acompanha o MS Office e serve de base para vários exemplos dados no Office.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
49
End Sub
Aqui, utilizamos o bloco With-End With com o Recordset (rs) para trabalhar com as
propriedades e métodos da classe. Primeiramente, checamos para saber se estamos no início do
arquivo (If Not .BOF8), pois não queremos iniciar o loop a meio caminho. Se não for
verdadeiro, move-se para o primeiro registro (MoveFirst). Feita a checagem, iniciamos o loop
utilizando EOF.
O nome completo do funcionário é composto pelo título, primeiro nome e sobrenome. A cada
passo do loop um nome completo é adicionado à nossa combobox.
Finalmente, terminamos o nosso código fechando todas as conexões:
Sub carregarDados(nomeBD As String, Tabela As String) frmDB.cboNome.ListIndex = 0 rs.Close: Set rs = Nothing conn.Close: Set conn = Nothing End Sub
Na própria sub-rotina, o primeiro valor da combobox é o valor cujo índice é zero. Observe que
utilizei os dois-pontos (:) para colocar na mesma linha o fechamento e limpeza dos objetos rs e
conn. Se isso lhe parecer complicado para leitura, coloque cada um em sua devida linha e
remova os dois-pontos.
O nosso código completa ficar, portanto:
8 BOF é a abreviação em inglês de “Beginning of File” (Início do Arquivo). O oposto é EOF “End of File”.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
50
Sub carregarDados(nomeBD As String, Tabela As String) Dim conn As ADODB.Connection Dim rs As ADODB.Recordset Set conn = New ADODB.Connection conn.Open "Provider=Microsoft.Jet.OLEDB.4.0; Data Source=" _ & nomeBD & ";" Set rs = New ADODB.Recordset rs.Open "Select * FROM " & Tabela & " ORDER BY FirstName", conn sobrenome = "LastName": priNome = "FirstName" título = "TitleOfCourtesy" With rs If Not .BOF Then .MoveFirst While Not .EOF nomeCompleto = .Fields(título) & " " & .Fields(priNome) _ & " " & .Fields(sobrenome) frmDB.cboNome.AddItem nomeCompleto .MoveNext Wend End With frmDB.cboNome.ListIndex = 0 rs.Close: Set rs = Nothing conn.Close: Set conn = Nothing End Sub
Os dados foram carregados para a combobox e agora precisamos distribuí-los para as caixas de
texto em nosso formulário. Novamente, estaremos criando uma sub para conectar ao nosso banco
de dados. Porém, desta vez, desejamos filtrar os dados de acordo com o um critério qualquer.
Para este exemplo, utilizaremos o primeiro nome (FirstName). Contudo, o filtro pode ser feito
com qualquer um dos campos disponíveis na tabela.
Como já passamos pelo processo de conexão ao BD, vamos direto ao código para filtrar os
dados:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
51
Sub AtualizarDados(nomeBD As String, Tabela As String, _ filtro As String)
Dim conn As ADODB.Connection Dim rs As ADODB.Recordset Set conn = New ADODB.Connection conn.Open "Provider=Microsoft.Jet.OLEDB.4.0; Data Source=" _ & nomeBD & ";" Set rs = New ADODB.Recordset rs.Open "SELECT * FROM " & Tabela & " WHERE FirstName = '" _ & filtro & "'", conn, , , adCmdText With frmDB .txtEnd.Text = rs.Fields("Address") .txtCidade.Text = rs.Fields("City") .txtCEP.Text = rs.Fields("PostalCode") .txtFone = rs.Fields("HomePhone") .txtMemo = rs.Fields("Notes") End With rs.Close: Set rs = Nothing conn.Close: Set conn = Nothing End Sub
Aqui, pouco muda. A “maior” diferença está no argumento adicional da sub-rotina (filtro) e em
como abrimos o Recordset (rs). Desta vez, ao invés de selecionar tudo na tabela, selecionamos
da tabela (Select*From Tabela) onde (Where) os registros sejam iguais ao filtro. Feita a
seleção dos itens que compõem o registro, distribuímos estes campos para as respectivas caixas
de textos.
Com as duas sub-rotinas prontas, precisamos agora colocá-las em uso. Primeiramente,
carregaremos os itens para a combobox:
Private Sub UserForm_Initialize() carregarDados ThisWorkbook.Path & "\DB\FPNWIND.mdb", "Employees" End Sub
Ao chamar a rotina que carrega os dados, entramos os dois argumentos pertencentes a sub-
rotina, isto é, o nome do banco de dados e a tabela que desejamos pesquisar.
Quando selecionamos um nome novo em nossa combobox, queremos que os dados do
funcionários sejam filtrados de acordo com o primeiro nome. Para tanto, utilizamos o evento
Change de nossa combobox para fazer isso:
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
52
Private Sub cboNome_Change() priNome = Split(cboNome.Text, " ") AtualizarDados ThisWorkbook.Path & "\DB\FPNWIND.mdb", _ "Employees", CStr(priNome(1)) End Sub
Mais uma vez precisamos chamar a rotina e acrescentar os argumento. Neste caso específico,
estamos usando o primeiro nome. Para obter o primeiro nome, utilizei a função Split9 para
separar os três itens que compõem o nome completo. Como Split retorna uma matriz e a base é
zero, o título está na posição 0, o primeiro nome na posição 1 e o sobrenome na posição 2. O
valor retornado e convertido para String (CStr), pois o argumento da sub-rotina é uma String.
A nossa conexão está feita. O primeiro nome da lista é mostrado quando acionamos o formulário:
Figura 9-3
Ao escolher um outro nome qualquer, as informações são atualizadas nos respectivos objetos:
9 A função Split não está disponível nas versões anteriores ao Excel 2002.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
53
Figura 9-4
OK, conectamos ao banco de dados, maneiro... mas só estamos lendo e nada mais. Embora seja
interessante ler as informações, é interessante também manipular tais informações. Isto é, como
acrescentamos um novo funcionário a nossa lista?
Antes de iniciarmos a nossa próxima questão, observe que estamos filtrando por primeiro nome.
O que ocorre quando o primeiro é igual? Bom, temos um grande problema! A verdade é que
nomes se repetem com muita freqüência e precisamos utilizar algo que seja único no filtro. A
figura abaixo mostra o que ocorre quando nomes são repetidos:
Figura 9-5
Ao invés de mostrar os dados para Robert Martin, ele mostra para Robert King.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
54
Para resolver o problema, utilizaremos a chave-primária, pois ela nos fornece um número único
em toda a tabela de funcionários.
O modelo desenvolvido adiante pode ser acessado em Form9.xls. Não abra o Form8 e Form9
simultaneamente. Embora cada um faça coisas distintas, ambos os arquivos contém os mesmos
formulários, com os mesmos nomes e sub-rotinas . Isso causará erros durante execução.
Antes de continuarmos, contudo, precisaremos modificar algumas coisas em nosso formulário.
Primeiramente modifique as seguintes propriedades da combobox, conforme a figura:
Figura 9-6
A primeira coluna da combobox guardará a chave-primária. Ao definir BoundColumn como sendo
2, estaremos mostrando o nome do funcionário ao invés da chave-primária. Defina a largura das
colunas (ColumnWidths) conforme a necessidade. Feita as mudanças, precisamos modificar
algumas coisas em nosso código, conforme abaixo:
Private Sub cboNome_Change() ID = cboNome.List(cboNome.ListIndex, 0) AtualizarDados ThisWorkbook.Path & "\DB\FPNWIND.mdb", _ "Employees", CLng(ID) End Sub
O ID é definido como sendo o valor que se encontra no índice “x” da combobox na coluna 1
(coluna 0, pois estamos usando Option Base 0). Como na tabela o tipo de dado para o ID é
Long (Longo) precisamos convertê-lo para evitar erro, pois os tipos de dados precisamos ser os
mesmos.
O código para carregamento dos dados para a combobox também precisa ser modificado. As
modificações não serão muitas, mas precisamos nos assegurar que os dados serão passados
corretamente.
O código completo é repetido abaixo (as partes novas em itálico):
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
55
Sub carregarDados(nomeBD As String, Tabela As String) Dim conn As ADODB.Connection Dim rs As ADODB.Recordset Dim List() Set conn = New ADODB.Connection conn.Open "Provider=Microsoft.Jet.OLEDB.4.0; Data Source=" _ & nomeBD & ";" Set rs = New ADODB.Recordset rs.Open "Select * FROM " & Tabela & " ORDER BY FirstName", conn sobrenome = "LastName": priNome = "FirstName" Título = "TitleOfCourtesy" If Not rs.BOF Then rs.MoveFirst n = 0 While Not rs.EOF n = n + 1 rs.MoveNext Wend ReDim List(n - 1, 1) i = 0 With rs If Not .BOF Then .MoveFirst While Not .EOF nomeCompleto = .Fields(Título) & " " & .Fields(priNome) _ & " " & .Fields(sobrenome) List(i, 0) = .Fields("EmployeeID") List(i, 1) = nomeCompleto 'Debug.Print List(i, 0) & " " & List(i, 1) i = i + 1 .MoveNext Wend End With With frmDB .cboNome.List = List .cboNome.ListIndex = 0 End With rs.Close: Set rs = Nothing conn.Close: Set conn = Nothing End Sub
A primeira modificação refere-se a nova variável List. O primeiro loop apenas serve para contar
o número de registros na vertical. Após a contagem, a matriz List é redimensionada e passa a
ter (n–1) linhas e duas colunas.
O próximo loop completa a matriz List com os dados que desejamos na coluna 1 (índice = 0) e
coluna 2 (índice = 1). O Debug.Print utilizei para assegurar que a matriz estava sendo
preenchida corretamente.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
56
Finalmente, com o formulário, defino a lista da combobox como sendo a List e inicio a
combobox no índice 0.
Agora, precisamos modificar algumas coisas na rotina que filtra os dados. Desta vez, será
repetido somente a parte modificada. Novamente, as partes críticas estão em itálico:
Sub AtualizarDados(nomeBD As String, Tabela As String, filtro As Long) rs.Open "SELECT * FROM " & Tabela & " WHERE EmployeeID =" _ & filtro, conn, , , adCmdText End Sub
A primeira modificação refere-se ao tipo de dado do filtro. Anteriormente, utilizamos String.
Como estamos avaliando um valor numérico Long, o filtro é definido como longo. A próxima
modificação é no SQL. Aqui, é necessário retirar o apóstrofo (‘). Se deixarmos o apóstrofo como
no primeiro exemplo, haverá um erro por incompatibilidade no formato dos dados.
Resolvido o problema da leitura dos dados, partiremos para o código que apagará e atualizará
registros no banco de dados.
Crie os novos botões conforme a figura abaixo:
Figura 9-7
Para o código do botão de remoção (Del. Registro), entraremos o seguinte código:
Private Sub cmdApagar_Click() ID = cboNome.List(cboNome.ListIndex, 0) delRegistro ThisWorkbook.Path & "\DB\FPNWIND.mdb", _ "Employees", CLng(ID) End Sub
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
57
Como podemos ver o código é igual ao utilizado na combobox, pois estamos procurando o
funcionário referente à ID para apagá-lo do BD. A evento chama o sub-rotina delRegistro.
Como já estamos proficientes em conexões ao BD, o código fica:
Sub delRegistro(nomeBD As String, Tabela As String, filtro As Long) Msg = "Ao apagar um registro, você não terá como desfazer a operação!" Msg = Msg & vbCr & vbCr & "Você tem certeza que deseja continuar?" Estilo = vbYesNo + vbInformation + vbDefaultButton2 Título = "Apagar registro..." Res = MsgBox(Msg, Estilo, Título) If Res = vbNo Then Exit Sub Dim conn As ADODB.Connection Dim rs As ADODB.Recordset Set conn = New ADODB.Connection conn.Open "Provider=Microsoft.Jet.OLEDB.4.0; Data Source=" _ & nomeBD & ";" Set rs = New ADODB.Recordset rs.Open "DELETE * FROM " & Tabela & " WHERE EmployeeID = " _ & filtro, conn, , , adCmdText Set rs = Nothing conn.Close Set conn = Nothing carregarDados ThisWorkbook.Path & "\DB\FPNWIND.mdb", "Employees" End Sub
Antes de tudo, queremos saber se o usuário realmente deseja apagar o registro. Se sim, o
processo continua caso contrário a sub-rotina é cancelada10.
A única coisa nova é o SQL. Ao invés de SELECT, utilizamos DELETE para apagar o registro. A
última linha recarrega os dados.
Estamos quase chegando ao final de nossa longa jornada no mundo do Excel e Access. Para
terminar, veremos como acrescentar um novo item ao nosso banco de dados. Para isso, foi criado
um novo formulário, conforme o modelo abaixo:
10 Exemplos com o estilo de MsgBox utilizado podem ser encontrados no Ajuda do VBA (procure por MsgBox Function)
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
58
A combobox Título utiliza os TitlesOfCourtesy do banco de dados. Adicione os títulos
utilizando um dos métodos já ensinados.
Para o botão Novo Registro, entraremos o seguinte código:
Private Sub cmdNovo_Click() novoRegistro ThisWorkbook.Path & "\DB\FPNWIND.mdb", "Employees" End Sub
Aqui, estamos chamando a sub-rotina novoRegistro da mesma forma que fizemos com todas
as sub-rotinas anteriores:
Sub novoRegistro(nomeBD As String, Tabela As String) Dim conn As ADODB.Connection Dim rs As ADODB.Recordset Set conn = New ADODB.Connection conn.Open "Provider=Microsoft.Jet.OLEDB.4.0; Data Source=" _ & nomeBD & ";" Set rs = New ADODB.Recordset rs.Open Tabela, conn, adOpenKeyset, adLockOptimistic, adCmdTable With frmNovoReg rs.AddNew rs.Fields("TitleOfCourtesy") = .txtTítulo rs.Fields("LastName") = .txtSobrenome rs.Fields("FirstName") = .txtPriNome rs.Fields("Address") = .txtEnd rs.Fields("City") = .txtCidade rs.Fields("PostalCode") = .txtCEP rs.Fields("HomePhone") = .txtFone
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
59
rs.Fields("Notes") = .txtMemo rs.Update End With Set rs = Nothing conn.Close Set conn = Nothing MsgBox "Registro adicionado com sucesso!", vbInformation, _ "Registro adicionado..." Unload frmNovoReg frmDB.Show 0 End Sub
Feito. Um novo registro é adicionado à tabela do banco de dados.
Em todas as sub-rotinas utilizadas para conexão ao BD, as rotinas requerem passagem de
parâmetros antes de continuar. Isso não é necessário. Se o leitor desejar rodar toda a sub-rotina
sem a passagem de parâmetros basta colocar os parâmetros dentro da própria sub-rotina.
A passagem de parâmetros flexibiliza a manipulação dos parâmetros que desejamos avaliar.
Terminamos aqui mais um passeio pelo mundo do Excel.
Série “Como Fazer”: Formulários no Excel utilizando VBA – Listbox e Combobox
Autor: Robert F Martim Criado em: 3/6/2004 11:03:00 Publicado: www.juliobattisti.com.br Última edição: 3/7/2004 20:18:00 Contato: [email protected]
60
10. Sobre o autor
Abaixo o leitor encontra um pequeno resumo do currículo e atividades do autor deste módulo:
FORMAÇÃO ACADÊMICA:
• Formado e Pós-Graduado em Finanças pela Universidade de Londres, Reino Unido
• Membro da Sociedade Brasileira de Econometria
LINGUAGENS DE PROGRAMAÇÃO E PLATAFORMAS:
• Visual Basic, Calculadores Programáveis Casio e Sharp
• BDs: MS Access and Lotus Approach
• Plataformas: Windows NT, 2000, XP, Linux Red Hat
EXPERIÊNCIA PROFISSIONAL
outubro 02- FAIRCOURT CAPITAL LIMITED (REINO UNIDO)
• Diretor TI
fev96-maio02 MELVALE GROUP (REINO UNIDO)
• Gerente de Exportação para a África Ocidental • Gerente de TI
OUTRAS ESPECIALIZAÇÕES
• Inspeção e regulamentações Nigerianas para importação e exportação (Nigerian-British Chamber of Commerce & Cotecna International)
• Procedimentos de exportação no Reino Unido (The Institute of Export, Reino Unido)
• ICC 500 e Incoterms (The Institute of Export, Reino Unido)
OUTRAS ATIVIDADES
Fornece suporte pro bono em TI à entidade de caridade Nigeriana NIDOE (Nigerians in Diaspora Organisation Europe) desde 2001. Participou ativamente na organização da conferência sobre Boa Governância e Responsabilidade Fiscal promovida pelo ONG em Abuja, Nigéria, em Novembro 2003. Foi um dos principais colaboradores na elaboração do relatório final sobre a conferência entregue a presidência da República Nigeriana em maio de 2004.
Autor do livro Excel e VBA na Modelagem Financeira: Uma abordagem prática (no prelo). Editora Axcel Books, 2004.
Colaborador ativo do fórum Excel Avançado do site www.júliobattisti.com.br, onde divide seu conhecimento e experiência com outros membros do espaço.