vbaformsoutlook

Switch from any view to email and then display a form


The trouble is the display switches, the form displays and then another instance of outlook pops on top which hides the form. I have to switch to the original instance to see the form. I suspect the code is quite untidy for what I am trying to achieve, so mods most welcome.

    Sub SF_ShowHEMform()
    Dim myOlExp As Outlook.Explorer
    Dim olApp As Outlook.Application
    Dim olNS As Outlook.Namespace
    Dim olFolder As Outlook.MAPIFolder
    
    Set olApp = Outlook.Application
    Set olNS = olApp.GetNamespace("MAPI")
    Set olFolder = olNS.GetDefaultFolder(olFolderInbox)
    
    olFolder.Display
    Set myOlExp = ActiveExplorer()
    myOlExp.WindowState = olMaximized
    
    Load sfHEMform
    sfHEMform.Show
    End Sub

11/07/2025 Update Research lead me to the code below but that fails with error 80010108 which is fairly common with Office developers on MS Answers.

    Set olApp = Outlook.Application
    Set olExp = olApp.ActiveExplorer
    Set olNS = olApp.GetNamespace("MAPI")
    Set olFolder = olNS.GetDefaultFolder(olFolderInbox)
  
    olExp.CurrentFolder = olNS.GetDefaultFolder(olFolderInbox)

Any suggestions why this does not work whereas Dmitry's option (2) does...?


Solution

  • A couple issues:
    1. Your code unconditionally displays a folder. You can instead check if there is an open Explorer already and make it switch to the folder in question.

    Off the top of my head:

    If olApp.Explorers.Count > 0 Then
     set olApp.Explorers(1).CurrentFolder = folder
    Else
      Folder.Display
    End If
    

    2. Your form is not a child of any of the Outlook windows. I don't think you can make it a child in VBA, but you can change its style to be always on top. You can call that function in your form's Initialize() method.

    Declare PtrSafe Function FindWindowA Lib "user32" (ByVal lpClassName As String, ByVal lpWindowName As String) As LongPtr
    Declare PtrSafe Function SetWindowPos Lib "user32" (ByVal hWnd As LongPtr, ByVal hWndInsertAfter As LongPtr, ByVal X As Long, ByVal Y As Long, ByVal cx As Long, ByVal cy As Long, ByVal wFlags As Long) As Long
    
    Public Const HWND_TOPMOST = -1
    Public Const SWP_NOSIZE = &H1
    Public Const SWP_NOMOVE = &H2
    Public Const SWP_NOACTIVATE = &H10
    
    Public Sub SetFormOnTop(frm As Object)
        Dim hWnd As LongPtr
        hWnd = FindWindowA("ThunderDFrame", frm.Caption)
        If hWnd <> 0 Then
            SetWindowPos hWnd, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOMOVE Or SWP_NOSIZE Or SWP_NOACTIVATE
        End If
    End Sub