VBA'用户定义类型未定义'与Outlook编译错误

时间:2022-11-05 08:35:22

I have a big Excel file that sends, with a command button, e-mails to Managers at work, and then they can press the button and it sends the files to Managers below them.

我有一个大的Excel文件,通过命令按钮发送电子邮件到工作中的经理,然后他们可以按下按钮,它将文件发送到他们下面的经理。

Since every manager has her/his own version of MS Office, I have a sub that checks which version (s)he has on her/his computer and marks V in References.

由于每个经理都有自己的MS Office版本,我有一个子程序可以检查他/她的计算机上有哪个版本,并在参考文献中标记为V.

When I save the file, I save it in a status that Outlook Object Library is not marked with V, and I have code that someone else built. The code runs through 3 subs. The first sub has a msgbox that when you answer on it, Yes , it sends you to next sub.

当我保存文件时,我将其保存为Outlook对象库未标记为V的状态,并且我有其他人构建的代码。代码贯穿3个子。第一个sub有一个msgbox,当你回答它时,是的,它会将你发送到下一个sub。

Public Sub before_send_mail()

    answer = MsgBox("Send Email?", vbYesNo + vbQuestion, "Empty Sheet")

    If answer = vbYes Then
        Call excel_ver
        Call sendMail
        Call remove_ref
    Else
     'do nothing
    End If

End Sub

Then, I have the "references picker by office version" that checks which version there is installed on the computer and marks V automatically in Tools---->References in Outlook object. That part seems to work well too.

然后,我有“办公室版本的参考选择器”,它检查计算机上安装的版本,并在Outlook对象的工具---->参考中自动标记V.那部分似乎也运作良好。

Sub excel_ver()

    On Error Resume Next
    ver = Application.Version

    If ver = 16 Then
        tmp_name = "C:\Program Files\Microsoft Office\Office16\MSOUTL.OLB"
        Application.VBE.ActiveVBProject.References.AddFromFile tmp_name
        Exit Sub
    End If

    If ver = 15 Then
        tmp_name = "C:\Program Files\Microsoft Office\Office15\MSOUTL.OLB"
        Application.VBE.ActiveVBProject.References.AddFromFile tmp_name
        Exit Sub
    End If

    If ver = 14 Then
        tmp_name = "C:\Program Files\Microsoft Office\Office14\MSOUTL.OLB"
        Application.VBE.ActiveVBProject.References.AddFromFile tmp_name
        Exit Sub
    End If

End Sub

And then we get to the problem. When I get to sub sendMail it gives me an error on the line Dim applOL As Outlook.Application

然后我们解决了这个问题。当我到sub sendMail时,它在Dim applOL As Outlook.Application行上给出了一个错误

Public Sub sendMail()

    Call ini_set

    If mail_msg.Cells(200, 200) = 1 Then

        lr = main_dist.Cells(main_dist.Rows.Count, "A").End(xlUp).Row

        On Error Resume Next

        For i = 2 To lr

            Application.DisplayAlerts = False

            Dim applOL As Outlook.Application 'Here is the error ---- that line
            Dim miOL As Outlook.MailItem
            Dim recptOL As Outlook.Recipient

            mail_msg.Visible = True

            mailSub = mail_msg.Range("B1")
            mailBody = mail_msg.Range("B2")

            mail_msg.Visible = False

            Set applOL = New Outlook.Application
            Set miOL = applOL.CreateItem(olMailItem)
            Set recptOL = miOL.Recipients.Add(main_dist.Cells(i, 5))
            recptOL.Type = olTo

            tempPath = ActiveWorkbook.Path & "\" & main_dist.Cells(i, 4) & ".xlsm"

            With miOL
                .Subject = mailSub
                .Body = mailBody
                .Attachments.Add tempPath
                .send     
            End With

            Set applOL = Nothing
            Set miOL = Nothing
            Set recptOL = Nothing

            Application.DisplayAlerts = True

        Next i
   End If
End Sub

2 个解决方案

#1


3  

Should run with no reference required:

应运行时无需参考:

Public Sub sendMail()

    Dim applOL As Object, miOL As Object, recptOL As Object
    Dim i As Long

    ini_set

    If mail_msg.Cells(200, 200) = 1 Then

        Set applOL = CreateObject("Outlook.Application")

        For i = 2 To main_dist.Cells(main_dist.Rows.Count, "A").End(xlUp).Row

            Set miOL = applOL.CreateItem(0)  'olMailItem=0
            Set recptOL = miOL.Recipients.Add(main_dist.Cells(i, 5))
            recptOL.Type = 1  ' olTo=1

            With miOL
                .Subject = mail_msg.Range("B1")
                .Body = mail_msg.Range("B2")
                .Attachments.Add ActiveWorkbook.Path & "\" & _
                                 main_dist.Cells(i, 4) & ".xlsm"
                .send
            End With
        Next i
        Set applOL = Nothing
   End If
End Sub

EDIT: in the code above I removed some of your "single-use" variables, but that's just my preference...

编辑:在上面的代码中,我删除了一些“一次性”变量,但这只是我的偏好......

#2


3  

During pre-compile process Outlook.Application is not valid as it is not set in Tools\References.... If you want to keep your code working you need to run ini_set first and before sendMail is even compiled. Try to add new subroutine to call both in a sequence:

在预编译过程中,Outlook.Application无效,因为它未在Tools \ References中设置....如果要保持代码正常工作,则需要先运行ini_set,然后再编译sendMail。尝试添加新子例程以按顺序调用它们:

Sub MainSub()
    call ini_set
    call sendMail
End Sub

To make it clear- remove Call ini_set from your sendMail and each time you have to call both do it from separate subroutine.

要清楚 - 从sendMail中删除Call ini_set,每次必须调用它们都从单独的子例程中执行。

Important! With this solution you could keep outlook appilcation constants (like olMailItem) which is not possible when you switch to Late binding solution.

重要!使用此解决方案,您可以保留Outlook appilcation常量(如olMailItem),这在切换到Late绑定解决方案时是不可能的。

#1


3  

Should run with no reference required:

应运行时无需参考:

Public Sub sendMail()

    Dim applOL As Object, miOL As Object, recptOL As Object
    Dim i As Long

    ini_set

    If mail_msg.Cells(200, 200) = 1 Then

        Set applOL = CreateObject("Outlook.Application")

        For i = 2 To main_dist.Cells(main_dist.Rows.Count, "A").End(xlUp).Row

            Set miOL = applOL.CreateItem(0)  'olMailItem=0
            Set recptOL = miOL.Recipients.Add(main_dist.Cells(i, 5))
            recptOL.Type = 1  ' olTo=1

            With miOL
                .Subject = mail_msg.Range("B1")
                .Body = mail_msg.Range("B2")
                .Attachments.Add ActiveWorkbook.Path & "\" & _
                                 main_dist.Cells(i, 4) & ".xlsm"
                .send
            End With
        Next i
        Set applOL = Nothing
   End If
End Sub

EDIT: in the code above I removed some of your "single-use" variables, but that's just my preference...

编辑:在上面的代码中,我删除了一些“一次性”变量,但这只是我的偏好......

#2


3  

During pre-compile process Outlook.Application is not valid as it is not set in Tools\References.... If you want to keep your code working you need to run ini_set first and before sendMail is even compiled. Try to add new subroutine to call both in a sequence:

在预编译过程中,Outlook.Application无效,因为它未在Tools \ References中设置....如果要保持代码正常工作,则需要先运行ini_set,然后再编译sendMail。尝试添加新子例程以按顺序调用它们:

Sub MainSub()
    call ini_set
    call sendMail
End Sub

To make it clear- remove Call ini_set from your sendMail and each time you have to call both do it from separate subroutine.

要清楚 - 从sendMail中删除Call ini_set,每次必须调用它们都从单独的子例程中执行。

Important! With this solution you could keep outlook appilcation constants (like olMailItem) which is not possible when you switch to Late binding solution.

重要!使用此解决方案,您可以保留Outlook appilcation常量(如olMailItem),这在切换到Late绑定解决方案时是不可能的。