Compartilhar via


Operador AddressOf

Um operador unário que faz com que o endereço do procedimento anterior seja transmitido para um procedimento de API que espera um ponteiro de função nessa posição na lista de argumentos .

Sintaxe

AddressOfprocedurename

O nome do procedimento necessário especifica o procedimento cujo endereço deve ser transmitido. Tem de representar um procedimento num módulo padrão no projeto no qual a chamada é feita.

Comentários

Quando um nome de procedimento aparece numa lista de argumentos, normalmente o procedimento é avaliado e o endereço do valor devolvido do procedimento é transmitido. AddressOf permite que o endereço do procedimento seja transmitido para uma função da API do Windows numa biblioteca de ligações dinâmicas (DLL), em vez de transmitir o valor devolvido do procedimento. Em seguida, a função API pode utilizar o endereço para chamar o procedimento Básico, um processo conhecido como chamada de retorno. O operador AddressOf só aparece na chamada ao procedimento da API.

Embora possa utilizar AddressOf para passar os ponteiros do procedimento entre os procedimentos Básicos, não pode chamar uma função através de tal ponteiro a partir do Nível Básico. Isto significa, por exemplo, que uma classe escrita no Nível Básico não pode efetuar uma chamada de retorno para o respetivo controlador utilizando esse ponteiro. Ao utilizar AddressOf para transmitir um ponteiro de procedimento entre os procedimentos no nível Básico, o parâmetro do procedimento chamado tem de ser escrito Como Longo.

A utilização de AddressOf pode causar resultados imprevisíveis se não compreender completamente o conceito de chamadas de retorno de funções. Tem de compreender como funciona a parte Básica da chamada de retorno e também o código da DLL para a qual está a transmitir o endereço da função. A depuração destas interações é difícil porque o programa é executado no mesmo processo que o ambiente de desenvolvimento. Em alguns casos, a depuração sistemática pode não ser possível.

Observação

Pode criar os seus próprios protótipos de função call-back em DLLs compilados com Microsoft Visual C++ (ou ferramentas semelhantes). Para trabalhar com AddressOf, o protótipo tem de utilizar a convenção __stdcall chamadas. A convenção de chamadas predefinida (__cdecl) não funcionará com AddressOf.

Uma vez que o chamador de uma chamada de retorno não está no seu programa, é importante que um erro no procedimento de chamada de retorno não seja propagado de volta para o autor da chamada. Pode fazê-lo ao colocar a instrução On Error Resume Next no início do procedimento de chamada de retorno.

Exemplo

O exemplo seguinte cria um formulário com uma caixa de listagem que contém uma lista ordenada alfabeticamente dos tipos de letra no seu sistema.

Para executar este exemplo, crie um formulário com uma caixa de listagem. O código do formulário é o seguinte:

Option Explicit

Private Sub Form_Load()
    Module1.FillListWithFonts List1
End Sub

Coloque o seguinte código num módulo. O terceiro argumento na definição da função EnumFontFamilies é um Valor Longo que representa um procedimento. O argumento tem de conter o endereço do procedimento, em vez do valor devolvido pelo procedimento. Na chamada para EnumFontFamilies, o terceiro argumento requer que o operador AddressOf devolva o endereço do procedimento EnumFontFamProc, que é o nome do procedimento de chamada de retorno que fornece ao chamar a função da API do Windows , EnumFontFamilies. O Windows chama EnumFontFamProc uma vez para cada uma das famílias de tipos de letra no sistema quando transmite AddressOf EnumFontFamProc para EnumFontFamilies. O último argumento transmitido para EnumFontFamilies especifica a caixa de listagem na qual as informações são apresentadas.

'Font enumeration types
Public Const LF_FACESIZE = 32
Public Const LF_FULLFACESIZE = 64

Type LOGFONT
        lfHeight As Long
        lfWidth As Long
        lfEscapement As Long
        lfOrientation As Long
        lfWeight As Long
        lfItalic As Byte
        lfUnderline As Byte
        lfStrikeOut As Byte
        lfCharSet As Byte
        lfOutPrecision As Byte
        lfClipPrecision As Byte
        lfQuality As Byte
        lfPitchAndFamily As Byte
        lfFaceName(LF_FACESIZE) As Byte
End Type

Type NEWTEXTMETRIC
        tmHeight As Long
        tmAscent As Long
        tmDescent As Long
        tmInternalLeading As Long
        tmExternalLeading As Long
        tmAveCharWidth As Long
        tmMaxCharWidth As Long
        tmWeight As Long
        tmOverhang As Long
        tmDigitizedAspectX As Long
        tmDigitizedAspectY As Long
        tmFirstChar As Byte
        tmLastChar As Byte
        tmDefaultChar As Byte
        tmBreakChar As Byte
        tmItalic As Byte
        tmUnderlined As Byte
        tmStruckOut As Byte
        tmPitchAndFamily As Byte
        tmCharSet As Byte
        ntmFlags As Long
        ntmSizeEM As Long
        ntmCellHeight As Long
        ntmAveWidth As Long
End Type

' ntmFlags field flags
Public Const NTM_REGULAR = &H40&
Public Const NTM_BOLD = &H20&
Public Const NTM_ITALIC = &H1&

'  tmPitchAndFamily flags
Public Const TMPF_FIXED_PITCH = &H1
Public Const TMPF_VECTOR = &H2
Public Const TMPF_DEVICE = &H8
Public Const TMPF_TRUETYPE = &H4

Public Const ELF_VERSION = 0
Public Const ELF_CULTURE_LATIN = 0

'  EnumFonts Masks
Public Const RASTER_FONTTYPE = &H1
Public Const DEVICE_FONTTYPE = &H2
Public Const TRUETYPE_FONTTYPE = &H4

Declare Function EnumFontFamilies Lib "gdi32" Alias _
     "EnumFontFamiliesA" _
     (ByVal hDC As Long, ByVal lpszFamily As String, _ 
     ByVal lpEnumFontFamProc As Long, LParam As Any) As Long
Declare Function GetDC Lib "user32" (ByVal hWnd As Long) As Long
Declare Function ReleaseDC Lib "user32" (ByVal hWnd As Long, _
     ByVal hDC As Long) As Long

Function EnumFontFamProc(lpNLF As LOGFONT, lpNTM As NEWTEXTMETRIC, _ 
     ByVal FontType As Long, LParam As ListBox) As Long
Dim FaceName As String
Dim FullName As String
    FaceName = StrConv(lpNLF.lfFaceName, vbUnicode)
    LParam.AddItem Left$(FaceName, InStr(FaceName, vbNullChar) - 1)
    EnumFontFamProc = 1
End Function

Sub FillListWithFonts(LB As ListBox)
Dim hDC As Long
    LB.Clear
    hDC = GetDC(LB.hWnd)
    EnumFontFamilies hDC, vbNullString, AddressOf EnumFontFamProc, LB
    ReleaseDC LB.hWnd, hDC
End Sub

Confira também

Suporte e comentários

Tem dúvidas ou quer enviar comentários sobre o VBA para Office ou sobre esta documentação? Confira Suporte e comentários sobre o VBA para Office a fim de obter orientação sobre as maneiras pelas quais você pode receber suporte e fornecer comentários.