+ Reply to Thread
Results 1 to 21 of 21

Send multiple emails to multiple recipients

Hybrid View

  1. #1
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Send multiple emails to multiple recipients

    Hello everyone
    I have a code that send one message to multiple recipients
    Sub Send_Multiple_Emails()
        Dim lastRow         As Long
        Dim I               As Long
        Dim strFolder       As String
        Dim mailObject      As Variant
        Dim outApp          As Variant
    
        strFolder = ThisWorkbook.Path & "\Files\"
        lastRow = Cells(Rows.Count, "A").End(xlUp).Row
    
        For I = 3 To lastRow
            Set mailObject = CreateObject("Outlook.Application")
            Set outApp = mailObject.CreateItem(0)
    
            With outApp
                .Subject = Range("B2").Value
                .Body = Range("C2").Value
                .To = Cells(I, 1).Value
                .Attachments.Add strFolder & Cells(2, 4).Value
                .Send
            End With
        Next I
    
        Set mailObject = Nothing
        Set outApp = Nothing
    
        MsgBox "Done...", 64
    Debugs:
        If Err.Description <> "" Then MsgBox Err.Description
    End Sub
    But I need to send multiple emails as attached and if possible make attachments optional by using check boxes for example

    Thanks advanced for help
    Attached Files Attached Files
    < ----- Please click the little star * next to add reputation if my post helps you
    Visit Forum : From Here

  2. #2
    Forum Expert Kenneth Hobson's Avatar
    Join Date
    02-05-2007
    Location
    Tecumseh, OK
    MS-Off Ver
    Office 365, Win10Home
    Posts
    2,573

    Re: Send multiple emails to multiple recipients

    The code that you posted simply sends emails per row. I would not say that it sends to multiple recipients unless preset in column A cells. It does not match your data as it seems to start at row 6 and your loop starts at row 3.

    You have merged cells so B2 and C2 will have no data for Subject and Body.

    As for the checkboxes you have none and if you did, what are the attachments? Do the files exist already, or generated and if so how?

    For just the sending email by row, I could modify your code but I like to use early binding for newer users to access intellisense.
    'More Excel to Outlook Examples: http://www.rondebruin.nl/win/s1/outlook/bmail4.htm
    'http://www.rondebruin.nl/win/s1/outlook/signature.htm
    
    'Add reference: Microsoft Outlook xx.x Library, where xx.x is 14.0, 15.0, 16.0, etc.
    Sub Main()
      Dim olApp As Outlook.Application, olMail As Outlook.MailItem
      Dim a() As Variant, r As Range, c As Range
      
      Set olApp = New Outlook.Application
      
      Set r = Range("A6", Range("A" & Rows.Count).End(xlUp))
      For Each c In r
        Set olMail = olApp.CreateItem(olMailItem)
        With olMail
          .To = c.Value             'Column A
          .Subject = c.Offset(, 1)  'Column B
          .Body = c.Offset(, 2)     'Column C
          .Display
          '.Send
        End With
      Next c
      
      Set olMail = Nothing
      Set olApp = Nothing
    End Sub

  3. #3
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Re: Send multiple emails to multiple recipients

    Thanks a lot Mr. Kenneth ...
    I had to arrange my ideas before posting. sorry for that
    Can check boxes added automatically in a separate code as I have a long list and it would be exhausting to add a check box for all?
    Here's a sample .. attachments are unknown in number may be one or more and may be none
    Attached Files Attached Files

  4. #4
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Re: Send multiple emails to multiple recipients

    Any help in this topic please?

  5. #5
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Re: Send multiple emails to multiple recipients

    I am still waiting Mr. kenneth
    Can you help me please?

  6. #6
    Forum Expert
    Join Date
    01-23-2013
    Location
    USA
    MS-Off Ver
    Microsoft 365 aka Office 365
    Posts
    3,863

    Re: Send multiple emails to multiple recipients

    Hi Yasser,

    See the attached zip file that contains a modified copy of your Excel File, and contains copies of your 3 sample data files in case anyone else wants to try to use the modified Excel file.

    The Excel file contains code to:
    a. Create/Delete CheckBoxes.
    b. Send Emails (using Outlook) to the User(s) on each data line with the appropriate attachments.

    To send one Email to multiple users, separate each Email address in Column 'A' with a semicolon (.

    The code does not close Outlook because most users keep Outlook open all the time.

    Please note that 'Late Binding' is used which avoids the necessity to have a VBA library reference to Outlook. For more information see:
    https://msdn.microsoft.com/en-us/library/0tcf61s1.aspx
    http://peltiertech.com/Excel/EarlyLateBinding.html

    Some newer versions of Outlook have NASTY Security messages when using VBA to access Outlook. The messages can be suppressed if your Anti-Virus software is up to date and you follow the following instructions:
    To prevent OutLook Security Message such as (and to remain secure):
    a. A program is trying to send an e-mail message on your behalf, or
    b. A program is trying to access e-mail addresses:

    Make sure Anti-Virus software is up to date
    Go to Windows 'Start' Menu
    Right Click on 'Outlook 2016' and select 'Run as Administrator'
    File > Options > Trust Center > Trust Center Settings > Programmatic Access
    AntiVirus status : Valid' should be displayed in the middle of the Screen.

    The Email code in Ordinary Code module Mod ModOutlookEmail follows:
    Option Explicit
    
    'SetForegroundWindow() is used by MoveFocusToWorksheet()
    #If VBA7 And Win64 Then
        '64 bit Excel:
        'All of the Win64 lines are supposed to be RED in 32 bit Excel
        Private Declare PtrSafe Function SetForegroundWindow Lib "user32" (ByVal HWnd As LongPtr) As Long
    
    #Else
        '32 bit Excel:
        Private Declare Function SetForegroundWindow Lib "user32" (ByVal HWnd As Long) As Long
    
    #End If
    
    'Reference: http://www.rondebruin.nl/win/s1/outlook/openclose.htm
    'Thank you Ron deBruin and Ben Clothier
    '
    'Late Binding is used in the following routines
    
    'Outlook enumeration constant reference: https://msdn.microsoft.com/en-us/library/office/aa219371(v=office.11).aspx
    Private Const olMinimized As Long = 1
    Private Const olMaximized As Long = 2
    Private Const olFolderInbox As Long = 6
    
    
    'Reference: http://www.globaliconnect.com/excel/index.php?option=com_content&view=article&id=170:automate-outlook-using-vba-sending-email-from-excel-using-outlook&catid=79&Itemid=475
    '
    'Chr(10) = linefeed between lines
    'Chr(13) = carriage return
    
    
    Sub SendMultipleEmailsWithAttachmentsUsingOutlook()
      'This sends multiple Emails with attachments with NO Preview
      
      Dim wb As Workbook
      Dim ws As Worksheet
      
      
      Dim iCountFailure As Long
      Dim iCountSuccess As Long
      Dim iError As Long
      Dim iLastRowUsed As Long
      Dim iNumberOfAttachments  As Long
      Dim iRow As Long
      
      Dim bNeedAttachments As Boolean
      
      Dim sAttachmentArray() As String
      Dim sAttachmentPath As String
      Dim sAttachmentPathAndFileName As String
      Dim sDisplayOrSendOption As String
      Dim sEmailAddress As String
      Dim sEmailBCC As String
      Dim sEmailBody As String
      Dim sEmailCC As String
      Dim sEmailSubject As String
      Dim sFileName As String
      Dim sMissingAttachmentList As String
      Dim sValue As String
      
      
      '''''''''''''''''''''''''''''''''''''''''''''''''''''''
      'Initialization
      '''''''''''''''''''''''''''''''''''''''''''''''''''''''
      
      'Create the Worksheet Object
      Set wb = ThisWorkbook
      Set ws = wb.ActiveSheet
      
      'Get the Last Row Used in Column 'A'
      iLastRowUsed = ws.Range("A:A").Find(What:="*", SearchOrder:=xlByRows, SearchDirection:=xlPrevious).Row
      
      
      '''''''''''''''''''''''''''''''''''''''''''''''''''''''
      'Get Email options
      '''''''''''''''''''''''''''''''''''''''''''''''''''''''
      
      'The 'Display or Send Option is one of':
      'a. 'Send'
      'b. 'Display'
      'c. 'Sendkeys'
      sDisplayOrSendOption = "Send"
      
      '''''''''''''''''''''''''''''''''''''''''''''''''''''''
      'Get the Email details from the SpreadSheet
      '''''''''''''''''''''''''''''''''''''''''''''''''''''''
      
      For iRow = 6 To iLastRowUsed
      
        'Initialize the Attachment Array and Attachment Data
        ReDim sAttachmentArray(1 To 1)
        iNumberOfAttachments = 0
        sMissingAttachmentList = ""
        
        'Get the Email address
        sEmailAddress = Trim(ws.Cells(iRow, "A").Value)
    
        'Get the 'Email Subject:'
        sEmailSubject = Trim(ws.Cells(iRow, "B").Value)
      
        'Get the Email 'Carbon Copy'
        sEmailCC = ""
      
        'Get the Email 'Blind Carbon Copy'
        sEmailBCC = ""
      
        sEmailBody = Trim(ws.Cells(iRow, "C").Value)
        
        sValue = UCase(Trim(ws.Cells(iRow, "F").Value))
        If sValue = "TRUE" Then
          bNeedAttachments = True
        Else
          bNeedAttachments = False
        End If
        
        If bNeedAttachments = True Then
        
          sAttachmentPath = ThisWorkbook.Path & "\Files\"
        
          'Attachment 1
          sFileName = Trim(ws.Cells(iRow, "G").Value)
          If Len(sFileName) > 0 Then
            sAttachmentPathAndFileName = sAttachmentPath & sFileName
            If Len(sAttachmentPathAndFileName) > 0 Then
              If LJMFileExists(sAttachmentPathAndFileName) = True Then
                iNumberOfAttachments = iNumberOfAttachments + 1
                ReDim Preserve sAttachmentArray(1 To iNumberOfAttachments)
                sAttachmentArray(iNumberOfAttachments) = sAttachmentPathAndFileName
              Else
                If Len(sMissingAttachmentList) = 0 Then
                  sMissingAttachmentList = sFileName
                Else
                  sMissingAttachmentList = sMissingAttachmentList & vbCrLf & sFileName
                End If
              End If
            End If
          End If
            
          'Attachment 2
          sFileName = Trim(ws.Cells(iRow, "H").Value)
          If Len(sFileName) > 0 Then
            sAttachmentPathAndFileName = sAttachmentPath & sFileName
            If Len(sAttachmentPathAndFileName) > 0 Then
              If LJMFileExists(sAttachmentPathAndFileName) = True Then
                iNumberOfAttachments = iNumberOfAttachments + 1
                ReDim Preserve sAttachmentArray(1 To iNumberOfAttachments)
                sAttachmentArray(iNumberOfAttachments) = sAttachmentPathAndFileName
              Else
                If Len(sMissingAttachmentList) = 0 Then
                  sMissingAttachmentList = sFileName
                Else
                  sMissingAttachmentList = sMissingAttachmentList & vbCrLf & sFileName
                End If
              End If
            End If
          End If
            
          'Attachment 3
          sFileName = Trim(ws.Cells(iRow, "I").Value)
          If Len(sFileName) > 0 Then
            sAttachmentPathAndFileName = sAttachmentPath & sFileName
            If Len(sAttachmentPathAndFileName) > 0 Then
              If LJMFileExists(sAttachmentPathAndFileName) = True Then
                iNumberOfAttachments = iNumberOfAttachments + 1
                ReDim Preserve sAttachmentArray(1 To iNumberOfAttachments)
                sAttachmentArray(iNumberOfAttachments) = sAttachmentPathAndFileName
              Else
                If Len(sMissingAttachmentList) = 0 Then
                  sMissingAttachmentList = sFileName
                Else
                  sMissingAttachmentList = sMissingAttachmentList & vbCrLf & sFileName
                End If
              End If
            End If
          End If
      
        End If
        
      
        If Len(sMissingAttachmentList) = 0 Then
          iError = SendEmailViaOutlook(sDisplayOrSendOption, sEmailAddress, sEmailCC, sEmailBCC, sEmailSubject, sEmailBody, sAttachmentArray)
      
          If iError = 0 Then
            'Normal processing - do nothing
            iCountSuccess = iCountSuccess + 1
          ElseIf iError = 1 Then
            'Could Not Open Outlook Error
            iCountFailure = iCountFailure + 1
            Call MoveFocusToWorksheet(ws)
            MsgBox "NOTHING DONE.  EMail NOT sent because Outlook could NOT be OPENED."
            GoTo MYEXIT
          ElseIf iError = 2 Then
            'Could Not Send Error
            iCountFailure = iCountFailure + 1
            Call MoveFocusToWorksheet(ws)
            MsgBox "NOTHING DONE.  EMail NOT sent due to Outlook 'Send' problem."
            GoTo MYEXIT
          Else
            'Could Not Open Outlook Error
            iCountFailure = iCountFailure + 1
            Call MoveFocusToWorksheet(ws)
            MsgBox "NOTHING DONE.  EMail NOT sent due to Unknown Error number " & iError & "."
            GoTo MYEXIT
          End If
        
        Else
          iCountFailure = iCountFailure + 1
          Call MoveFocusToWorksheet(ws)
          MsgBox "NOTHING DONE for the Email on Row " & iRow & "." & vbCrLf & _
                 "The following data files DO NOT EXIST:" & vbCrLf & _
                 "Folder: " & sAttachmentPath & vbCrLf & _
                 sMissingAttachmentList
        End If
      
      Next iRow
      
      Call MoveFocusToWorksheet(ws)
      MsgBox "Done..." & vbCrLf & _
             iCountSuccess & " Emails Sent Successfully." & vbCrLf & _
             iCountFailure & " Emails NOT sent.", 64
      
      
    MYEXIT:
    
       'Clear object pointers
       Set wb = Nothing
       Set ws = Nothing
    
    End Sub
    
    
    Function SendEmailViaOutlook(sDisplayOrSendOption As String, _
                                 sTo As String, _
                                 sCC As String, _
                                 sBCC As String, _
                                 sSubject As String, _
                                 sBody As String, _
                                 sAttachmentArray() As String) As Long
      'This sends an e-mail via Outlook
      '
      'Return Values: 0 = No Error
      '               1 = Could not create Outlook object (Outlook could not be opened)
      '               2 = Could Not Send the message (runtime error 429 is OK)
      '
      'Outlook objects are created using 'Late Binding' (no library reference required)
      '
      'Multiple recipients are separated by a semi-colon:
      'For example: .CC = "person1@email.com;person2@email.com"
      '
      'If using .Display,  SendKeys "^{ENTER}" can be placed before the 'With OutMail' line.
      'This assumes 'SendKeys' works in the version of Excel.
      
      Dim OutApp As Object
      Dim OutMail As Object
      
      Dim i As Long
      Dim iError As Long
        
      'Disable Events and Screen Updating
      Application.EnableEvents = False
      Application.ScreenUpdating = False
     
     
      'Get the Outlook Objectif Outlook is already open
      On Error Resume Next
      Set OutApp = LjmOpenOutlook()
      
      'Exit if the Outlook Object could not be created
      If OutApp Is Nothing Then
        iError = 1
        GoTo MYEXIT
      End If
      
      'Create the Outlook Mail Object
      Set OutMail = OutApp.CreateItem(0)
     
      'Determine the values to be sent
      With OutMail
        .To = sTo
        .CC = sCC
        .BCC = sBCC
        .Subject = sSubject
        .Body = sBody
        
        If Len(sAttachmentArray(1)) > 0 Then
          For i = 1 To UBound(sAttachmentArray)
           .Attachments.Add sAttachmentArray(i)
            Debug.Print i, sAttachmentArray(i)
          Next i
        End If
        
        If sDisplayOrSendOption = "Send" Then
          .Send
          If iError = 0 Or iError = 429 Then
            'Do nothing - Send probably worked OK
          Else
            'Send Failure
            iError = 2
            GoTo MYEXIT
          End If
        ElseIf sDisplayOrSendOption = "Display" Then
          .Display
        Else
          .Display
          Application.Wait (Now + TimeValue("0:00:02"))  'SENDKEYS does not appear to work with this code
          Application.SendKeys "%s", True                '% = ALT --->  Sending 'ALT s'
        End If
      End With
      
    MYEXIT:
      'Resume normal error processing
      On Error GoTo 0
     
      'Reenable Events and Screen Updating
      Application.EnableEvents = True
      Application.ScreenUpdating = True
     
      'Clear the Object Pointers
      Set OutMail = Nothing
      Set OutApp = Nothing
      
      'Set the return value
      SendEmailViaOutlook = iError
      
    End Function
    
    Private Function LJMFileExists(sPathAndFullFileName As String) As Boolean
      'This returns TRUE if a file exists and FALSE if a file does NOT exist
      
      Dim iError As Integer
      Dim iFileAttributes As Integer
    
      On Error Resume Next
      iFileAttributes = GetAttr(sPathAndFullFileName)
         
      'Check the internal error  return
      iError = Err.Number
      Select Case iError
        Case Is = 0
            iFileAttributes = iFileAttributes And vbDirectory
            If iFileAttributes = 0 Then
              LJMFileExists = True
            Else
              LJMFileExists = False
            End If
        Case Else
            LJMFileExists = False
      End Select
    
      On Error GoTo 0
    
    End Function
    
    Private Function LjmOpenOutlook( _
        Optional iWindowState As Long = olMinimized, _
        Optional bReleaseIt As Boolean = False _
        ) As Object
      'This opens outlook if it is NOT already open
      'Reference: http://www.rondebruin.nl/win/s1/outlook/openclose.htm
      'Thank you Ron deBruin and Ben Clothier
      '
      'Late Binding is used in the following routines
      
      Static myStaticOutlookObject As Object
      
      On Error GoTo ERROR_HANDLER
     
      Select Case True
            
        Case myStaticOutlookObject Is Nothing, Len(myStaticOutlookObject.Name) = 0
          Set myStaticOutlookObject = GetObject(, "Outlook.Application")
          If myStaticOutlookObject.Explorers.Count = 0 Then
    INIT_OUTLOOK:
            'Open the Outlook inbox to prevent errors with security prompts
            'Set the requested Outlook Windows state (i.e. Minimized, Maximized)
            myStaticOutlookObject.Session.GetDefaultFolder(olFolderInbox).Display
            myStaticOutlookObject.ActiveExplorer.WindowState = iWindowState
          End If
            
        Case bReleaseIt
          'Clear the STATIC Outlook Object if requested by the input option
          Set myStaticOutlookObject = Nothing
          
      End Select
        
      'Set the return value
      Set LjmOpenOutlook = myStaticOutlookObject
      GoTo MYEXIT
    
    ERROR_HANDLER:
     Select Case Err.Number
        Case -2147352567
          'User cancelled setup, silently exit
          Set myStaticOutlookObject = Nothing
        Case 429, 462
          'Error 462 - Outlook is NOT open
          Set myStaticOutlookObject = GetOutlookApp()
          If myStaticOutlookObject Is Nothing Then
            Err.Raise 429, "LjmOpenOutlook", "Outlook Application does not appear to be installed."
          Else
            Resume INIT_OUTLOOK
          End If
        Case Else
          MsgBox "Error " & Err.Number & ": " & Err.Description, vbCritical, "Unexpected error attempting to OPen Outlook."
      End Select
        
    MYEXIT:
      Exit Function
          
    End Function
    Lewis

    The remainder of the code and code for CheckBoxes is in the next post due to size restrictions.
    Last edited by LJMetzger; 01-23-2017 at 02:02 PM. Reason: Added 'Late Binding' info

  7. #7
    Forum Expert
    Join Date
    01-23-2013
    Location
    USA
    MS-Off Ver
    Microsoft 365 aka Office 365
    Posts
    3,863

    Re: Send multiple emails to multiple recipients

    Previous post continued:

    Remainder of the code in Module ModOutlookEmail:
    Private Function GetOutlookApp() As Object
      'This returns a pointer to the Outlook Object if Outlook is available
      '
      'This function is used exclusively by LjmOpenOutlook() and is part of the
      'original Ron deBruin code referenced above
      
      Dim myOutlookObject As Object
    
      'Attempt to create an Outlook object
      On Error Resume Next
      Set myOutlookObject = CreateObject("Outlook.Application")
      On Error GoTo 0
        
      'Clear any error that occurs and also clear the object
      If Err.Number <> 0 Then
        Err.Clear
        Set myOutlookObject = Nothing
      End If
      
      'Set the return value
      Set GetOutlookApp = myOutlookObject
    
      'Clear the local object pointer
      Set myOutlookObject = Nothing
    
    End Function
    
    Sub MoveFocusToWorksheet(ws As Worksheet)
      'This moves the focus from another application (e.g. Outlook) back to Excel
      '
      'Reference: http://stackoverflow.com/questions/28042521/set-focus-back-to-the-application-window-after-showing-userform
      'Thank you Gene Skuratovsky
      
      'Put the focus on the Workbook and Worksheet from the input parameter
      ws.Parent.Activate
      ws.Activate
      
      'Move the above Workbook/Worksheet to the front
      Call SetForegroundWindow(Application.HWnd)
        
    End Sub
    CheckBox code in Ordinary Code Module ModFormsCheckBoxes:
    Option Explicit
    
    Sub DeleteAllFormsCheckBoxesOnActiveSheet()
      'This deletes all Shapes on the Active Sheet that start with 'Check' (CASE INSENSITIVE)
    
      Dim Sh As Object
      Dim iCount As Long
      Dim sLinkedCellAddress As String
      Dim sName As String
        
      For Each Sh In ActiveSheet.Shapes
        sName = Sh.Name
        If UCase(Left(sName, Len("CHECK"))) = "CHECK" Then
          iCount = iCount + 1
          
          sLinkedCellAddress = Sh.ControlFormat.LinkedCell
          If sLinkedCellAddress <> "" Then
            ActiveSheet.Range(sLinkedCellAddress) = ""
          End If
          
          Sh.Delete
        End If
        
      Next Sh
    
      MsgBox iCount & " Forms CheckBoxes deleted from Sheet '" & ActiveSheet.Name & "'."
    
    End Sub
    
    
    Sub AddFormsCheckBoxesToActiveCell()
      'This Adds a Forms CheckBox to the LAST 'Active Cell'
    
      Dim sCell As String
      
      sCell = ActiveCell.Address
      Call AddFormsCheckBoxes(sCell)
      
    End Sub
    
    Sub AddFormsCheckBoxesToAllSelectedCells()
      'This Adds a Forms CheckBoxes to the Selected Cells
      
      Dim sCell As String
      
      On Error Resume Next
      sCell = Selection.Address
      If Err.Number <> 0 Then
        Err.Clear
        MsgBox "There were no cells selected on the Active Sheet."
        On Error GoTo 0
        Exit Sub
      End If
      
      On Error GoTo 0
      Call AddFormsCheckBoxes(sCell)
      
    End Sub
    
    Sub AddFormsCheckBoxes(sRange As String)
      'This adds Forms Checkboxes to the Selected Cells
      '
      'Existing CheckBoxes in a cell are deleted
    
      Const xCheckBoxHeight = 12
      Const xCheckBoxWidth = 12
    
      Dim Sh As Object
      
      Dim r As Range
      
      Dim iCheckBoxNumber As Long
      Dim iLen As Long
      Dim iMaxCheckBoxNumber As Long
      
      Dim xHeight As Double
      Dim xLeft As Double
      Dim xTop As Double
      Dim xWidth As Double
    
      Dim sCheckBoxName As String
      Dim sName As String
      Dim sValue As String
      
      'Get the length constant value
      iLen = Len("CHECKBOX")
      
      For Each r In Range(sRange)
     
        'Get the dimensions of the active cell
        xHeight = r.Height
        xLeft = r.Left
        xTop = r.Top
        xWidth = r.Width
    
        'Calculate starting point for the new 'Forms Check Box'
        xLeft = xLeft + (xWidth - xCheckBoxWidth) / 2#
        xTop = xTop + (xHeight - xCheckBoxHeight - 2) / 2#
      
        'Assign the 'CheckBox Name' to include the 'Address' (e.g. 'CheckBoxB5')
        sCheckBoxName = "CheckBox" & r.Address(False, False)
        
        'Delete the CheckBox if it already exists
        If LjmShapeExists(ActiveSheet.Name, sCheckBoxName) = True Then
          ActiveSheet.Shapes(sCheckBoxName).Delete
        End If
        
        
        'Add the 'Forms' Check Box
        'Link the 'Check Box' to the underlying Cell
        'Initialize the value to Unchecked (Initialize first to Checked to make formulas register)
        With ActiveSheet.CheckBoxes.Add( _
           Left:=xLeft, _
           Top:=xTop, _
           Width:=xCheckBoxWidth, _
           Height:=xCheckBoxHeight)
            
          .Characters.Text = ""
          .LinkedCell = r.Address
          .Name = sCheckBoxName
          .Value = xlOn
          .Value = xlOff
          '.OnAction = "FormsCheckBoxEventHandler"   'Commented Out - Event Handler not needed in this situation
        End With
      
        'Hide the contents of the Underlying Cell
        r.NumberFormat = ";;;"
      
      Next r
      
    End Sub
    
    
    Sub FormsCheckBoxEventHandler()
      'This Process Forms Check Box events
      '
      'NOTE: Off = -4146 = xlOff
      '      On  =      1 = xlOn
      
      Dim iValue As Long
      
      Dim sCaller As String
      Dim sLinkedCellAddress As String
      Dim sValue As String
      
      'Get the name of the Checkbox that caused the event
      sCaller = Application.Caller
      
      'Get the CheckBox Value
      iValue = ActiveSheet.Shapes(sCaller).ControlFormat.Value
      If iValue = xlOff Then
        sValue = "FALSE"
      Else
        sValue = "TRUE"
      End If
      
      MsgBox "FormsCheckBoxEventHandler called by " & sCaller & "  value is " & iValue & " equals " & sValue
      
    End Sub
    
    Function LjmShapeExists(sSheetName As String, sShapeName As String) As Boolean
      'This returns 'True' if a Shape with a specific name EXISTS on the Input Sheet
    
      Dim Sh As Shape
         
      'Attempt to set the 'Shape' object
      On Error Resume Next
      Set Sh = Sheets(sSheetName).Shapes(sShapeName)
      On Error GoTo 0
      
      'Return 'True' if the Shape object exists
      If Not Sh Is Nothing Then
        LjmShapeExists = True
      End If
      
      'Clear object pointer
      Set Sh = Nothing
      
    End Function

  8. #8
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Re: Send multiple emails to multiple recipients

    That's amazing and fascinating Mr. Lewis
    I liked it a lot
    You are wonderful. Thanks a lot for this masterpiece

  9. #9
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Re: Send multiple emails to multiple recipients

    Hello again Mr. Lewis
    Sorry for disturbing you in this topic again
    I need any one of these options to work (don't need all of them, any one will do):

    * Ability to add an outlook signature.
    * Ability to format text like color, weight and size.
    * Ability to put html in the body field.

  10. #10
    Forum Expert
    Join Date
    01-23-2013
    Location
    USA
    MS-Off Ver
    Microsoft 365 aka Office 365
    Posts
    3,863

    Re: Send multiple emails to multiple recipients

    To add an Outlook signature see the code associated with Post #6 in the following thread: http://www.excelforum.com/showthread...t=#post4570827

  11. #11
    Forum Expert
    Join Date
    01-23-2013
    Location
    USA
    MS-Off Ver
    Microsoft 365 aka Office 365
    Posts
    3,863

    Re: Send multiple emails to multiple recipients

    The following code uses HTML tags to format text in the Outlook body. The code has references to a couple of links to HTML references. In the code you have to use
    .HtmlBody
    
    'not
    
    .Body
    Try the following sample Macro. To simplify the code, Outlook MUST be open before running this Macro. If Outlook is NOT open, and the code fails, you may have to Close and then Reopen Excel to get the code to work.
    Sub SimpleOutlookEmailDiplayWithTextColor()
      'This assumes that Outlook is already open to simplify the code
      
      'Reference: http://www.w3schools.com/html/html_paragraphs.asp
      'Reference: http://www.html.am/html-codes/text/
      
      Dim OutApp As Object
      Dim OutMail As Object
      
      
     'Attempt to create an Outlook object
      On Error Resume Next
      Set OutApp = GetObject(, "Outlook.Application")
      If Err.Number <> 0 Then
        Err.Clear
        msgbox "NOTHING DONE.  The Outlook Object could not be created from Excel." & vbCrLf & _
               "Try again when Outlook is open."
        Exit Sub
      End If
      On Error GoTo 0
      
      
      'Create the Outlook Mail Object (using the default Email account)
      Set OutMail = OutApp.CreateItem(0)
     
      'Determine the values to be sent
      With OutMail
        .To = ""
        .CC = ""
        .BCC = ""
        .Subject = "Info Request"
        .htmlbody = "The ExcelForum firewall DOES NOT ALLOW HTML code - see the attached file for complete working code."
       
        
        .display
        
        '.Send - comment out the 'Display line' if you want to send
      End With
      
      'Clear the Object Pointers
      Set OutMail = Nothing
      Set OutApp = Nothing
    
    End Sub
    Lewis

  12. #12
    Forum Expert Kenneth Hobson's Avatar
    Join Date
    02-05-2007
    Location
    Tecumseh, OK
    MS-Off Ver
    Office 365, Win10Home
    Posts
    2,573

    Re: Send multiple emails to multiple recipients

    The .htmlBody method to get a signature after a .Display as Lewis showed in that link is an easy way to do the signature. Of course standard html coding as Lewis also demonstrated is an easy way to make html code if you know the syntax.

    Other ways to add a signature and a routine to convert a range to html (RangeToHTML) is shown at Ron's site.
    'More Excel to Outlook Examples: http://www.rondebruin.nl/win/s1/outlook/bmail4.htm
    'http://www.rondebruin.nl/win/s1/outlook/signature.htm

  13. #13
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Re: Send multiple emails to multiple recipients

    After some tries I found that the code in Post 6 in the link attached have the solution as I have to display first
    OutMail.Display
    Then within With statement to display again (I don't know if this is relevant or not) then assign
    .HTMLBody = sEmailBody & .HTMLBody
    then finally .Send

    Or it is enough to change .body to .HTMLBody

    Sorry for the confusion
    Regards

  14. #14
    Forum Expert Kenneth Hobson's Avatar
    Join Date
    02-05-2007
    Location
    Tecumseh, OK
    MS-Off Ver
    Office 365, Win10Home
    Posts
    2,573

    Re: Send multiple emails to multiple recipients

    I don't see why that would not work. Of course using that method, you must have a signature set to display for new emails.
    'https://www.mrexcel.com/forum/excel-questions/986338-excel-email-attachment-not-including-form-items.html#post4733697
    Sub SendEmailButtonERFQ_Click()
      Dim Source As Range, Dest As Workbook
      Dim TempFilePath$, TempFileName$, FileExtStr$
      Dim FileFormatNum&, OutApp As Object, OutMail As Object
      Dim strbody$, signature$, i%, destFN$
      
      With Application
        .ScreenUpdating = False
        .EnableEvents = False
        .DisplayAlerts = False
      End With
    
      TempFilePath = Environ$("temp") & "\"
      TempFileName = "XXXX"
    
      Set Dest = Workbooks.Add(xlWBATWorksheet)
    
      'Copy sheet1 to Dest wb.
      With Dest
        ThisWorkbook.Worksheets(1).Copy before:=.Worksheets(1)
        'Delete empty worksheets in dest.
        On Error Resume Next
        For i = 2 To .Worksheets.Count
          Worksheets(i).Delete
        Next i
        On Error GoTo 0
      End With
    
      If Val(Application.Version) < 12 Then
        'You use Excel 97-2003
        FileExtStr = ".xls": FileFormatNum = -4143
      Else
        'You use Excel 2007-2016
        FileExtStr = ".xlsx": FileFormatNum = 51
      End If
      
      destFN = TempFilePath & TempFileName & FileExtStr
      Dest.SaveAs destFN
      Dest.Close True
    
      strbody = "Hello," & _
        "XXXX" & "<br>" & _
        "XXXX" & _
        "Due Date: " & ThisWorkbook.Sheets("Sheet1").Range("D8").Value & _
        "Please confirm receipt of this e-mail and acknowledgement" _
        & "of due date." & _
        "XXXX" & "<br>" & _
        "Thanks," & "<br>"
    
      Set OutApp = CreateObject("Outlook.Application")
      Set OutMail = OutApp.CreateItem(0)
    
      With OutMail
        .Display
        signature = .HTMLBody
        .To = "ken@gmail.com"
        .CC = ""
        .BCC = "" 'Insert
        .Subject = "Pricing Request: " & _
          ThisWorkbook.Sheets("Sheet1").Range("D3").Value & _
          " Due Date: " & ThisWorkbook.Sheets("Sheet1").Range("D8").Value
        .HTMLBody = strbody & signature
        .Attachments.Add destFN
        'You can add other files also like this
        '.Attachments.Add ("C:\test.txt")
        '.Display
        .Send
      End With
        
      On Error GoTo 0
    
      Kill TempFilePath & TempFileName & FileExtStr
      Set OutMail = Nothing
      Set OutApp = Nothing
    
      With Application
        .ScreenUpdating = True
        .EnableEvents = True
        .DisplayAlerts = True
      End With
    End Sub

  15. #15
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Re: Send multiple emails to multiple recipients

    Thanks a lot for very helpful replies.
    I tried to add signature as illustrated in post 10 and it is ok .. But after formatting the signature in Outlook, I found that it is sent plain with no formatting
    Tried to change this line
    sSignature = OutMail.Body
    to this line
    sSignature = OutMail.HTMLBody
    But doesn't work .. and I got the message scrambled in signature
    Any idea how to keep the format of signature?

  16. #16
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Re: Send multiple emails to multiple recipients

    @Mr. Lewis
    Please be patient with me. I am just a beginner in the aspect of Outlook
    As for your awesome file in post #6 .. How can I add signature parts? as I am lost in the lines of code
    Please don't attach a new file as I need to learn. Just point me the name of the procedure and the line at which I need to add or edit to be able to follow changes
    Thanks advanced for help

  17. #17
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Re: Send multiple emails to multiple recipients

    Hello Mr. Kenneth
    I tested your code and it worked ... Just I have to open the Outlook after running the code...
    I don't know why it doesn't send directly without the need of reopening the outlook .. But generally it is working well

  18. #18
    Forum Expert
    Join Date
    01-23-2013
    Location
    USA
    MS-Off Ver
    Microsoft 365 aka Office 365
    Posts
    3,863

    Re: Send multiple emails to multiple recipients

    Yasser asked: How can I add signature parts? ...point me the name of the procedure and the line at which I need to add or edit to be able to follow changes
    In post #6 See Sub SendEmailViaOutlook() in code Module ModOutlookEmail .

    The best way to answer is through an annotated example. First we will start with a relatively simple working code example. To add to the simplicity, Outlook MUST be open before the code is run from Excel.

    The example does the following:
    a. Uses the Default Outlook Account as the sender
    b. Uses the default Outlook Signature
    c. Uses a simple HTML text message
    Option Explicit
    
    Sub SimpleOutlookEmailDiplayWithTextBodyAndSignature()
      'This assumes that Outlook is already open to simplify the code
      
      'Reference: http://www.w3schools.com/html/html_paragraphs.asp
      'Reference: http://www.html.am/html-codes/text/
      
      Dim OutApp As Object
      Dim OutMail As Object
      
      Dim sHtmlBody As String
      Dim sSignature As String
      
      
     'Attempt to create an Outlook object
      On Error Resume Next
      Set OutApp = GetObject(, "Outlook.Application")
      If Err.Number <> 0 Then
        Err.Clear
        msgbox "NOTHING DONE.  The Outlook Object could not be created from Excel." & vbCrLf & _
               "Try again when Outlook is open."
        Exit Sub
      End If
      On Error GoTo 0
      
      'Create the Body of the Email
      sHtmlBody = _
        "This is line one of the email body." & "<BR>" & _
        "This is line two." & _
        "This is a continuation of line two."
    
      
      'Create the Outlook Mail Object (using the default Email account)
      Set OutMail = OutApp.CreateItem(0)
      
      
      'Display the Default Signature (If Any) - it is contained in .HTMLBody
      'If there is no default signature, nothing is displayed
      OutMail.display
      sSignature = OutMail.htmlbody
     
      'Determine the values to be sent
      With OutMail
        .To = ""
        .CC = ""
        .BCC = ""
        .Subject = "Info Request"
        .htmlbody = sHtmlBody & sSignature
        .display
        
        '.Send - comment out the 'Display line' if you want to send
      End With
      
      'Clear the Object Pointers
      Set OutMail = Nothing
      Set OutApp = Nothing
    
    End Sub
    Now to describe what various parts of the code are used for.
    This opens Outlook only if it is already open using 'Late Binding'. For examples of 'Early Binding' vs 'Late Binding' see:http://www.excelforum.com/showthread.php?t=1020212
    Early Binding is Excel version dependent and requires use of a VBA Library reference. If moving code between computers that use different versions of Office, the other computer must explicitly open the 'Library Reference' on the new computer.
    Late Binding is version independent. However, if Outlook Constants are used, their values must be explicitly used.

    For Outlook Constants and their values see: https://msdn.microsoft.com/en-us/lib...ffice.11).aspx
    Set OutApp = GetObject(, "Outlook.Application")
    The Email body is saved in a separate string variable and can go anywhere in the code prior to the .Body or .HTMLBody statement that uses the variable. When using a Signature that contains something other than straight text, the Email body must use the HTML "<br>" as an EOL (End of Line) indicator. "<br>" is roughly equivalent to vbCrLf (Carriage Return - Linefeed) or vbLf (Linefeed) depending on the EOL convention of the computer. If the Body and Signature combination use Text only, the .Body statement is used and I use vbCrLf as the EOL character.
    Dim sBody as string
    sBody = _
          "This is line one of the email body." & vbCrLf & _
          "This is line two." & _
          "This is a continuation of line two."
    If the Body or Signature contains HTML (and/or picture in the Signature) , the .HTMLBody statement is used and "<BR>" must be used as the EOL character.
    Dim sHtmlBody As String
    sHtmlBody = _
        "This is line one of the email body." & "<BR>" & _
        "This is line two." & _
        "This is a continuation of line two."
    After the 'Outlook Application' object is created, a 'Mail Object' must be created. The 'Mail Object' references a specific account which is usually Account '0' (the Default Account). If Outlook has 5 different Email accounts, then the Email address with Account 4 can be used as shown below.
    'Create the Outlook Mail Object (using the default Email account)
    Set OutMail = OutApp.CreateItem(0)
    
    'or
    
    'Create the Outlook Mail Object (using the Email address associated with Account '4')
    Set OutMail = OutApp.CreateItem(4)
    The 'Mail Object' does the rest of the work. There is no specific VBA command to get a signature, so a little trickery is required. If the Email body is BLANK the .Display command will display the Signature associated with the 'Mail Object' (a specific Email address). The signature can then be saved for later use.
    Dim sSignature As String
    'Display the Default Signature (If Any) - it is contained in .HTMLBody
    'If there is no default signature, nothing is displayed
    OutMail.display
    sSignature = OutMail.htmlbody

    Most of the following items are self-explanatory:
      'Determine the values to be sent
    With OutMail
      .To = "a@b.com;c@d.com"
      .CC = ""    'Carbon Copy
      .BCC = ""   'Blind Carbon Copy (other recipients don't know this person sees the Email)
      .Subject = "Info Request"
    
      '...
    End With
    Combine the Email Body and the Signature
    With OutMail
      '...
      .htmlbody = sHtmlBody & sSignature
      '...
    End With
    Add attachements if any
    With OutMail
      '...
      .Attachments.Add "H:\abc.docx"
      .Attachments.Add "H:\def.docx"
      '...
    End With
    Finally,
    a. To Display the Email in Outlook for Editing and review in Outlook:
    With OutMail
      '...
      .Display
      '...
    End With
    or

    a. To Send the Email to Outlook in the 'Send Queue'. This command DOES NOT send the message. Outlook is usually configured to Send/Receive periodically or to Send/Receive on Manual Commands by the User. The Email will be ACTUALLY SENT according to the Outlook setup.
    With OutMail
      '...
      .Send
      '...
    End With
    To send the Email NOW is a topic for a completely different thread at some future time.

    Lewis
    Last edited by LJMetzger; 01-30-2017 at 10:36 AM.

  19. #19
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Re: Send multiple emails to multiple recipients

    Awesome Awesome Awesome. Thank you very much Mr. Lewis for this free and awesome tutorial
    It is incredible in fact. I love it a lot
    Thanks a lot for the time you spent to post that extremely fantastic explanation

    Waiting for the future topic (Send the Email NOW)
    Best and Kind regards

  20. #20
    Forum Expert
    Join Date
    01-23-2013
    Location
    USA
    MS-Off Ver
    Microsoft 365 aka Office 365
    Posts
    3,863

    Re: Send multiple emails to multiple recipients

    Additional HTML information. When you want to use different fonts, font sizes, bold, color, etc., HTML code is needed, but you don't have to know HTML. There are several techniques that can be used in addition to typing the HTML from Scratch, including:

    a. Using one of the many free HTML editors available for downloading including the one referenced from the above link (which I have not tried): http://www.html.am/html-codes/text/

    b. Using a combination of Microsoft Word and your favorite text editor such as NotePad.
    (1) Create the look and feel you want in Microsoft Word.
    (2) Save the file as a .htm file
    (3) Open the file using your favorite text editor
    (4) Cut and paste the body text at the bottom of the .htm file into your VBA code.

    Lewis

  21. #21
    Forum Expert
    Join Date
    04-23-2009
    Location
    Matrouh, Egypt
    MS-Off Ver
    Excel 2013
    Posts
    6,892

    Re: Send multiple emails to multiple recipients

    Thanks a lot Mr. Lewis for this additional and useful information
    I think this is an easy way instead of learning html

+ Reply to Thread

Thread Information

Users Browsing this Thread

There are currently 1 users browsing this thread. (0 members and 1 guests)

Similar Threads

  1. Replies: 0
    Last Post: 04-17-2015, 06:01 AM
  2. Sending emails to multiple recipients through VBA
    By MikeFranz123 in forum Excel Programming / VBA / Macros
    Replies: 5
    Last Post: 04-17-2014, 09:47 AM
  3. [SOLVED] Macro To Send Emails with PDF: Multiple Emails and PDF's
    By totoga12 in forum Excel Programming / VBA / Macros
    Replies: 16
    Last Post: 03-19-2014, 06:13 PM
  4. send email to multiple recipients
    By plans in forum Excel Programming / VBA / Macros
    Replies: 11
    Last Post: 03-18-2014, 09:26 AM
  5. Macro to send multiple attachments to several recipients
    By dave1983 in forum Excel Programming / VBA / Macros
    Replies: 1
    Last Post: 03-21-2013, 11:07 AM
  6. send email from excel to multiple recipients
    By hariexcel1987 in forum Excel Programming / VBA / Macros
    Replies: 22
    Last Post: 01-13-2013, 01:41 PM
  7. Send email to multiple recipients
    By Court16 in forum Excel Programming / VBA / Macros
    Replies: 1
    Last Post: 03-24-2009, 05:20 PM

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts

Search Engine Friendly URLs by vBSEO 3.6.0 RC 1