How to wait for events without blocking Windows messages?

This is a question on how to maintain a C # stream while waiting for events.

I am writing a C # application that should launch an outlook instance (or reuse any existing instance if there is one active), create a mail item and show it, and then wait for the close event or send an event for the mail item,

The application will not be an add-in running inside Outlook, but will be executed from outside outlook to create an instance of outlook and mailitem.

Since my application does not work from gui outlook, but rather launches gui outlook, I somehow need to support my process until events are received (sending or closing). If my application returns and dies after displaying an Outlook message, my event handlers will also be dead.

Question: How should I support the application while waiting for events?

Since my thread is the one that creates the mail item and displays it in the Outlook window, is my thread responsible for not blocking the delivery of possible messages to the perspective window?

My thought was to have a method similar to this method to keep the process waiting

while(!MailClosed){ lock(mailLock){ Monitor.Wait(mailLock); } } 

and then allow event handlers to send and close another method call to wake the waiter when they handle the event

 private void SignalClose(){ lock(mailLock){ MailClosed = true; Monitor.Pulse(mailLock); } } 

Would this block make possible messages from delivery to a perspective window containing my mail item? Does anyone have a better solution to handle this situation?

+4
source share
2 answers

You can use ApplicationContext to maintain a message loop.

I'm not sure if the example below is what you are looking for, but I will give it a try.

 static class Program { private static ApplicationContext _context; [STAThread] static void Main() { Application.EnableVisualStyles(); Application.SetCompatibleTextRenderingDefault(false); using (_context = new ApplicationContext()) { var message = new OutlookMailMessage(); message.Closed += new EventHandler(message_Closed); Application.Run(_context); } } static void message_Closed(object sender, EventArgs e) { // Perform processing after the message has been send or closed. _context.ExitThread(); } } 

In the above code, the ApplicationContext starts, which you can use instead of displaying the Form . This holds the message loop until the ExitThread call is ExitThread . With this, you can use the message event handler to close or send an event to do some processing, and then exit the application using the ExitThread method.

+4
source

If you are worried about blocking calls, you can run the Outlook instance in a separate thread, then your main thread can Thread.Sleep () in this while loop so that it doesn't check so often.

My solution is not elegant, but you're probably not too worried about a lot of deadlocks, so it should work.

0
source

Source: https://habr.com/ru/post/1337440/


All Articles