How to delay the initialization of an Outlook Addin?

Add-in Express™ Support Service
That's what is more important than anything else

How to delay the initialization of an Outlook Addin?
 
David Liebeherr




Posts: 11
Joined: 2013-05-22
Hello,

currently I am using the ADXAddinModule.AddinStartupComplete event to initialize my outlook addin.
However this means that my addin gets initialized before the outlook explorer window is shown (and fully loaded).
Is there a way to delay the initialization of my addin to the point in time when the outlook explorer window is shown and fully loaded?
I have also tried the ADXOutlookAppEvents.Startup and ADXOutlookAppEvents.ExplorerActivate events without much change.

I want to delay the initialization because a) the initialization takes some time and I don't want the user to stare at the outlook splash screen for some while and b) when my addin is started for the first time it opens a "welcome to this app follow these steps to set it up" window (via ShowDialog()) and right now when the window is shown the outlook splash screen is still visisble.

I have also tried to use a BackgroundThread or the ThreadPool to do the initialization.
But unfortunately this seems to be not an option because in the initialization i need to do certain things that must be done in the outlook main thread (like accessing the outlook model). So I get all sorts of multithread/crossthread issues when not doing the initialization in the main thread.

Thank you in advance!

Sincerely yours,
David Liebeherr
Posted 22 May, 2013 00:17:23 Top
Andrei Smolin


Add-in Express team


Posts: 16588
Joined: 2006-05-11
Hello David,

You can start a timer e.g. in ExplorerActivate.

As to using threads, you are correct: you must access the Outlook object model in the main thread.

You can use the fact that the OnSendMessage event of the add-in module occurs on the main thread: call ADXAddinModule.SendMessage(%a custom message%) to perform some task on the main thread.

What do you think?

Regards from Belarus (GMT+3),

Andrei Smolin
Add-in Express Team Leader
Posted 22 May, 2013 03:03:20 Top
David Liebeherr




Posts: 11
Joined: 2013-05-22
Hello Andrei,

thank you for your quick response.
That is a very interesting tip to use SendMessage and it seems to be a good option.

I will try that.

Are there any disadvantages using this technique and are there any trap doors to watch for when using this?

Thank you very much.

Sincerely yours,
David Liebeherr
Posted 22 May, 2013 16:21:57 Top
Andrei Smolin


Add-in Express team


Posts: 16588
Joined: 2006-05-11
Hello David,

Here's a template use of this approach:


private const int WM_USER = 0x0400;
private const int MYMESSAGE = WM_USER + %an integer > 0%;
//...

private void MyMethod(object sender)
{  this.SendMessage (MYMESSAGE);  }

private void AddinModule_OnSendMessage(object sender, AddinExpress.MSO.ADXSendMessageEventArgs e)
{
if (e.Message == MYMESSAGE)
   {  //... }
}


David Liebeherr writes:
Are there any disadvantages using this technique and are there any trap doors to watch for when using this?


Nothing that we are aware of.

Regards from Belarus (GMT+3),

Andrei Smolin
Add-in Express Team Leader
Posted 23 May, 2013 03:47:44 Top
David Liebeherr




Posts: 11
Joined: 2013-05-22
Hello Andrei,

thank you for the template.
It is working like a charm in principle.
But unfortunately this technique can not solve my actual problem.

I can delay the initialization of my addin with a Timer/Background Thread (with Thread.Sleep), but the problem is that I cannot determine which delay (e.g. 1, 2 or 5 Seconds) I have to use to get the initialization done AFTER the Outlook Main Window has been loaded.
If I choose a too low timespan then the init will occur before the outlook main window is loaded and if I choose a too long timespan the init will be delayed for an unnecessary long time.

So the problem is that I can not use a time based delay.
I need some kind of event that is triggered after the outlook main window has been loaded (and preferrably completely drawn).
Is there any such kind of event available?

I already tried OutlookEvents.ExplorerActivate, but this event is actually raised before the outlook main window is completely loaded.

Remember: My problem is that when my addin starts for the very first time it will show a "welcome" dialog.
This dialog should be shown after the outlook main window was loaded.
Otherwise when the welcome dialog is shown the outlook splash screen will still be visible.

I guess my problem is also related to the fact that I show the welcome dialog by calling Window .ShowDialog() (it is a WPF window, but I guess the same applies to a Windows Forms form).
But if I use Window .Show() my window will be hidden behind the outlook main window once it is loaded.

Anyway, thanks for the things you have suggested.

Sincerely yours,
David Liebeherr
Posted 23 May, 2013 19:33:29 Top
David Liebeherr




Posts: 11
Joined: 2013-05-22
Hi,

I think I have found a solution:
If I subscribe to the ADXAddinModule.OnRibbonLoaded event and call ADXAddinModule.SendMessage (based on the template code you provided) from my event handler it seems to do the trick.

My welcome dialog is shown after the outlook main window has loaded.

I know that this technique will probably not work with any outlook version before outlook 2007 (becuase outlook 2003 and before doe not have a ribbons), but my Addin does not support pre outlook 2007 anyway.

So thank you Andrei for your help, I think my problem is solved.

Sincereley yours,
David Liebeherr
Posted 23 May, 2013 19:47:27 Top
Andrei Smolin


Add-in Express team


Posts: 16588
Joined: 2006-05-11
Hello David,

If it works then okay.

Just FYI, there's an overload of the System.Windows.Forms.Form.Show() method that allows specifying the owner window.

Regards from Belarus (GMT+3),

Andrei Smolin
Add-in Express Team Leader
Posted 24 May, 2013 05:51:26 Top
nwein




Posts: 544
Joined: 2011-03-28
Sorry to barge in here but Andrei:
Just FYI, there's an overload of the System.Windows.Forms.Form.Show() method that allows specifying the owner window .

The Show expects an IWin32Window object. As far as I'm aware Office applications are not IWin32Window .
I know that because I've had to do a lot of things to make it work like I wanted.
Is there something I've missed? Is it possible to assign a form an Office application as its owner?
Posted 24 May, 2013 10:27:47 Top
Andrei Smolin


Add-in Express team


Posts: 16588
Joined: 2006-05-11
Hello Nir,

To "convert" an Office window to IWin32Window, you need to get the HWND of that window and use this class (taken from http://ryanfarley.com/blog/archive/2004/03/23/465.aspx):

C#:
public class WindowWrapper : System.Windows.Forms.IWin32Window
{
    public WindowWrapper(IntPtr handle)
    {
        _hwnd = handle;
    }

    public IntPtr Handle
    {
        get { return _hwnd; }
    }

    private IntPtr _hwnd;
}


VB:
Public Class WindowWrapper
Implements System.Windows.Forms.IWin32Window

Dim theHandle As IntPtr

Public Sub New(ByVal aHandle As System.IntPtr)
theHandle = aHandle
End Sub

Public ReadOnly Property Handle() As System.IntPtr _
Implements System.Windows.Forms.IWin32Window.Handle
Get
Return theHandle
End Get
End Property
End Class


The very same wrapper works in IE and this should work in Office too.

In Outlook, you use ADXAddinModule.GetOutlookWindowHandle(anOutlookWindowObject). "anOutlookWindowObject" can be an object of the Outlook.Explorer and Outlook.Inspector type.

In Excel, you use Application.Hwnd and Window.Hwnd properties.

Regards from Belarus (GMT+3),

Andrei Smolin
Add-in Express Team Leader
Posted 24 May, 2013 11:08:00 Top
nwein




Posts: 544
Joined: 2011-03-28
Oh wow, did not know that.
This is great, thank you!
Posted 24 May, 2013 11:27:30 Top