Поздняя привязка для кода Excel VBA, не зависящего от версии

У меня есть электронная таблица Excel, из которой извлекается мой код VBA для создания встреч в общем календаре Outlook. Им будут манипулировать несколько менеджеров проектов (конечно, не одновременно).

Я обнаружил, что у пары пользователей есть более старая версия Office, и поэтому я узнал, что должен использовать позднее связывание, чтобы сделать его совместимым со старыми версиями.

Как преобразовать то, что у меня есть, в позднее связывание. Все примеры, которые мне понадобились для создания этого кода, были ранними связываниями.

Option Explicit
    
Sub SCHMTG() 'Schedule Meeting
    
    Dim wb As Workbook
    Set wb = ThisWorkbook
    
    Dim ws As Worksheet
    Set ws = wb.Sheets("Projects")
    
    ws.Unprotect ""
    
    Dim check As Boolean
    check = False
    
    Dim o As Outlook.Application
    Set o = New Outlook.Application
    
    Dim oNS As Outlook.Namespace
    Set oNS = o.GetNamespace("MAPI")
    
    Dim FOL As Outlook.MAPIFolder
    Set FOL = oNS.GetFolderFromID("00000000F4EFC638C1F878469E872F63F51D794A0100F96BCFC3DAF87B4F8C66193C3EA6F4F40000029DA2430000")
    
    Dim oAPT As Outlook.AppointmentItem
    Dim oAPT_DATE As Date
    Dim oAPT_TIME As Date
    Dim oOBJECT As Object
    Dim b As CheckBox
    Dim r As Integer
    Dim c As Integer
    
    Set b = ws.CheckBoxes(Application.Caller)
    With b.TopLeftCell
        r = .Row
        c = .Column
    End With
    
    For Each oAPT In FOL.Items 'Search for existing meeting
                
        oAPT_DATE = Format(oAPT.Start, "MM-DD-YYYY")
        oAPT_TIME = TimeValue(oAPT.Start)
        
        If oAPT_DATE = ws.Cells(r, c - 3).Value And oAPT.Subject = ws.Cells(r, 1).Value And oAPT_TIME = ws.Cells(r, c - 2).Value Then
            check = True
        Else
        End If
    
    Next oAPT
    
    If check = False Then 'If no meeting already exist Then create new meeting
        Set oAPT = FOL.Items.Add(olAppointmentItem)
        With oAPT
            .Start = ws.Cells(r, c - 3).Value + ws.Cells(r, c - 2).Value
            .Duration = ws.Cells(r, c - 1).Value * 60
            .Subject = ws.Cells(r, 1).Value & " " & ws.Cells(1, c).Value
            .Body = "Project: " & ws.Cells(r, 1).Value & vbCrLf & "Location: " & ws.Cells(r, 2) & vbCrLf & "OASIS#: " & ws.Cells(r, 3) & vbCrLf & "Project Manager: " & ws.Cells(r, 5) & vbCrLf & "Distributor: " & ws.Cells(r, 8) & vbCrLf & "Assigned Technitian: " & ws.Cells(r, c - 5) & vbCrLf & "Date: " & ws.Cells(r, c - 3) & vbCrLf & "Start Time: " & Format(ws.Cells(r, c - 2), "h:mm am/pm") & vbCrLf & "Duration: " & ws.Cells(r, c - 1) & " Hour(s)"
            .Location = ws.Cells(r, 2).Value
            .Recipients.Add Cells(r, c - 4).Value
            .MeetingStatus = olMeeting
            .ReminderMinutesBeforeStart = 1440
            .Save
            .Send
        End With
        ws.Cells(r, c - 1).Locked = True
        ws.Cells(r, c - 2).Locked = True
        ws.Cells(r, c - 3).Locked = True
        ws.Cells(r, c - 5).Locked = True
    Else
    End If
    
    ws.Cells(r, 1).Locked = True
    ws.Cells(r, 2).Locked = True
    ws.Cells(r, 3).Locked = True
    
    ws.Protect "", True, True
    
End Sub

person Adstanley84    schedule 13.11.2017    source источник
comment
также я использую Excel 2016, и у меня есть один пользователь в 2015 году и один в 2010 году.   -  person Adstanley84    schedule 14.11.2017


Ответы (1)


Удалите все ссылки проекта VBA на библиотеку Outlook.

Объявляйте любые объекты Outlook As Object вместо использования имени типа библиотеки Outlook. Используйте CreateObject() вместо New

eg:

Dim oAPT As Outlook.AppointmentItem
Dim o As Outlook.Application
Set o = New Outlook.Application

было бы

Dim oAPT As Object
Dim o As Object
Set o = CreateObject("Outlook.Application")

Любые производные от Outlook константы, такие как olAppointmentItem, должны быть либо объявлены как константы в вашем коде, либо заменены их числовыми значениями (которые вы можете найти с помощью обозревателя объектов).

person Tim Williams    schedule 13.11.2017
comment
О, хорошо, вместо: Dim FOL As Outlook.MAPIFolder Set FOL = oNS.GetFolderFromID("FolderID") я бы использовал: Dim FOL As Object Set FOL = oNS.GetFolderFromID("FolderID") - person Adstanley84; 14.11.2017
comment
Извините за плохое форматирование, я сдался после редактирования в 10-й раз, и это было так близко, как я мог - person Adstanley84; 14.11.2017
comment
Да - вы пробовали это? - person Tim Williams; 14.11.2017
comment
хорошо, я внес изменения, которые вы предложили, однако теперь я получаю ошибки еще в нескольких строках. Set oAPT = FOL.Items.Add(olAppointmentItem) oAPT_DATE = Format(oAPT.Start, "MM-DD-YYYY") 'says Format Cannot find Project Library - person Adstanley84; 14.11.2017
comment
Я видел, как это выдавало мне ошибку Set oAPT = FOL.Items.Add(olAppointmentItem) после того, как я снял отметку с отсутствующей библиотеки объектов Outlook 16 в ссылках. - person Adstanley84; 14.11.2017
comment
Просто к вашему сведению. Я учился программировать на VBA около 2 недель, поэтому мои знания ограничены. Я просто делаю это, чтобы создать инструмент для моего отдела. - person Adstanley84; 14.11.2017
comment
olAppointmentItem — это константа, определенная в справочнике по Outlook, поэтому, как только вы снимите флажок, ваш VBA не будет знать, что это такое. Вам нужно добавить Const olAppointmentItem = 1, чтобы сообщить вашему коду, каково его значение. И если вы получаете ошибки, полезно точно описать, что это за ошибка. - person Tim Williams; 14.11.2017
comment
Спасибо! это сработало. Мне нужно было определить еще пару констант, но это помогло. Теперь он работает на всех моих рабочих станциях пользователей. - person Adstanley84; 14.11.2017
comment
Рад слышать, что ты понял это. - person Tim Williams; 15.11.2017