Solved

Automate outlook - modify a 'reply' email from another office app.

Posted on 2016-11-24
10
19 Views
Last Modified: 2016-11-30
Using an instance of the outlook namespace I can use the CreateItem to create and manipulate a new email message, leaving it available for the user to add text or other things at will then send it.

Now there is a requirement that the user selects an email message and hits 'reply' to start editing a new email.  At this point when the email editor window is open
-SNAG-0003.bmpthat via VBA I can get the item and manipulate it as if it was a new item generated by my current code.  How?
0
Comment
Question by:AndyAinscow
  • 6
  • 4
10 Comments
 
LVL 19

Expert Comment

by:darbid73
Comment Utility
At least in Outlook 2010 and 2013 but maybe earlier you can use the MailItem.Reply event.

Option Explicit
Private WithEvents oExpl As Explorer
Private WithEvents oItem As MailItem
Private bDiscardEvents As Boolean
'http://slipstick.me/44b0w
 
Private Sub Application_Startup()
   Set oExpl = Application.ActiveExplorer
   bDiscardEvents = False
End Sub
 
Private Sub oExpl_SelectionChange()
   On Error Resume Next
   Set oItem = oExpl.Selection.Item(1)
End Sub
 
' Reply
Private Sub oItem_Reply(ByVal Response As Object, Cancel As Boolean)
       
   Cancel = True
   bDiscardEvents = True
  
   Dim oResponse As MailItem
   Set oResponse = oItem.Reply

' add the fields here
   oResponse.Subject = "keyword " & oResponse.Subject

   oResponse.Display
      
   bDiscardEvents = False
Set oItem = Nothing
End Sub

Open in new window

Source for the code is here. I have just copied fully.

To explain what is happening is that (1) you get the Outlook Explorer.  (2) This Explorer has an item selection event. (3) You get the MailItem from this event. (4) Listen for the Reply on this MailItem.

I think this code might need a little but of adjusting but in general its a good way.
0
 
LVL 44

Author Comment

by:AndyAinscow
Comment Utility
Thanks, I'll give it a try and let you know.
0
 
LVL 44

Author Comment

by:AndyAinscow
Comment Utility
I've given it a try (after qualifying some things - the code is meant to be run inside outlook I think).  It will find the selected email message in the main outlook window.  Unfortunately this is not the window where one is composing the reply which means it could even be another email message.  With dire consequences if it is then modified.  Also that will always find an email even when no reply is being composed - again not what I need.

The critical thing is I need to find the reply to an email in its pop up window - should one be being composed.
0
 
LVL 19

Expert Comment

by:darbid73
Comment Utility
Welcome to the complications of Outlook.

1. Outlook can have more than one Explorer window.  For example if you have a Calendar window open and Email window then this will mean you have more than one Explorer.
2. As a consequence of 1 if you have an instance of the Calendar window then you will never get an EmailItem.
3. A SelectionChange event is for ALL selections. This means that if you select a CalendarItem or Note or Task then this event is fired.  But it is my understanding that you MUST select a MailItem before you can reply.
4. As such if you have the correct Explorer then you will get the Selection Events and thus it will on selection of an email set up the Reply event.  Now when you click on reply the event is fired.

Please follow the steps I am explaining and understand them and let me know at the exact point you are having difficulty.
0
 
LVL 44

Author Comment

by:AndyAinscow
Comment Utility
I'm pretty certain I understand what you are saying.

I'm running the code from another office app, not inside outlook.  Because of that I have to cope with the situation that the user has started a reply before running the code.  In this case hooking into an event isn't going to work - because the event has been fired before I even get an instance of outlook in my code.
So I need to find the 'reply' window if it exists and is open.  Put another way, from an instance of outlook I need to be able to iterate through all child windows and reliably identify a 'reply' window which I can then use to modify the email being generated.  This should also be done from VBA.  

(In theory I could code a dll which iterates through existing child windows and looks for a specific class type of window - Spy++ can help me find the correct type that outlook will use - but then I end up with a window handle which I would have to somehow get back to the VBA code and 'convert' to an existing window.  That 'window' would then allow me to edit the email programatically - add specific attachments, check all necessary recipients will be sent the mail.)
0
How your wiki can always stay up-to-date

Quip doubles as a “living” wiki and a project management tool that evolves with your organization. As you finish projects in Quip, the work remains, easily accessible to all team members, new and old.
- Increase transparency
- Onboard new hires faster
- Access from mobile/offline

 
LVL 19

Accepted Solution

by:
darbid73 earned 500 total points
Comment Utility
When your app starts you will also need to use this collection Inspectors.

An Inspector is a "window" where you see a mailItem / Calendar item / Task etc.

Dim oApp As Outlook.Application 'replace this with however you get your Outlook application

            Dim myInspectors As Outlook.Inspectors
            Dim i As Integer

            myInspectors = oApp.Inspectors

            If oApp.Inspectors.Count = 0 Then
                'no inspectors so nothing to do get out of here
                Return
            End If

            For i = 0 To oApp.Inspectors.Count - 1

                Dim itemObject As Object = oApp.Inspectors.Item(i)

                If (TypeOf itemObject Is Outlook.MailItem) Then
                    Dim mailItem As Outlook.MailItem = TryCast(itemObject, Outlook.MailItem)

                    'you now have a mailItem type and need to determine the type of mail item
                End If


            Next

Open in new window


Checking which mailItem is a reply mailitem like you want is apparently not easy, and honestly something I have never had to do.  This thread seems to answer it.  I would take what Ken Slovak MVP as the way to do it. He has written books on Outlook from 2007 so I assume he knows what he is saying.
0
 
LVL 44

Assisted Solution

by:AndyAinscow
AndyAinscow earned 0 total points
Comment Utility
Some problems with that code - it is VB not VBA.  However it does seem to have pointed me in the direction I want to go:

    Dim mailItem As Outlook.mailItem
    
    If objOutlook.Inspectors.Count > 0 Then
        Set mailItem = objOutlook.ActiveInspector.CurrentItem
    End If
    
    If mailItem Is Nothing Then
        Set mailItem = objOutlook.CreateItem(olMailItem)
    End If

....

Open in new window

0
 
LVL 44

Author Closing Comment

by:AndyAinscow
Comment Utility
I think it is good enough to close this thread off at this point.  Thanks.
0
 
LVL 19

Expert Comment

by:darbid73
Comment Utility
oppps sorry.

But you do not want this
If mailItem Is Nothing Then
        Set mailItem = objOutlook.CreateItem(olMailItem)
    End If

Open in new window

0
 
LVL 44

Author Comment

by:AndyAinscow
Comment Utility
Yes I do.  It could be the user has NOT click reply to anything so there is no message waiting to be manipulated.
The original situation was just simply create a new mail message.  Now there has been the requirement that ** if ** they were in the process of replying then they could go back to the other office app and hit a button to add things to the reply.  (No flipping back and forth, copy and pasting).

OK.  It is not bullet proof and the user can always do something silly but it should work in the vast majority of instances.
0

Featured Post

Highfive Gives IT Their Time Back

Highfive is so simple that setting up every meeting room takes just minutes and every employee will be able to start or join a call from any room with ease. Never be called into a meeting just to get it started again. This is how video conferencing should work!

Join & Write a Comment

Set OWA language and time zone in Exchange for individuals, all users or per database.
Resolve DNS query failed errors for Exchange
Get people started with the process of using Access VBA to control Outlook using automation, Microsoft Access can control other applications. An example is the ability to programmatically talk to Microsoft Outlook. Using automation, an Access applic…
This video shows how to remove a single email address from the Outlook 2010 Auto Suggestion memory. NOTE: For Outlook 2016 and 2013 perform the exact same steps. Open a new email: Click the New email button in Outlook. Start typing the address: …

743 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

16 Experts available now in Live!

Get 1:1 Help Now