在Outlook中生成新消息并显示为模式 [英] Generate new message in Outlook and display as modal

查看:118
本文介绍了在Outlook中生成新消息并显示为模式的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我需要使用Outlook从应用程序生成和发送消息. 邮件表单应显示为模式表单,主要是因为我生成了附件,并且在用户发送电子邮件(或将其丢弃)时应将其删除.

I need to generate and send message with Outlook from application. Mail form should be displayed as modal, mostly because i generate attachment and it should be deleted when user send email (or discard it).

我的问题是当我使Outlook对话框成为模态("MailIt.Display(True)")时,Outlook消息窗口在后台显示.命令"Outlook.ActiveWindow.Activate"将其放在最前面,但是当窗口已经可见时可以调用它,因此如果窗口是模式窗口,则无法调用它.我尝试了这段代码:

My problem is when i make Outlook dialog modal ("MailIt.Display(True)"), Outlook message window shown in background. Command "Outlook.ActiveWindow.Activate" brings it to front, but it can be called when windows already visible and so i can't call it if window is modal. I tried this code:

MailIt.Display(False);
OleVariant(Outlook.ActiveWindow).Activate;
MailIt.Display(True);

但是id不起作用,如果表单已经显示为正常模式,则无法切换为模式.有任何想法吗? 我的环境:Windows 8(已禁用UAC),XE3,Outlook 2010.

But id doesn't work, if form already displayed it normal mode it can not be switched to modal. Any ideas? My environment: Windows 8 (UAC disabled), XE3, Outlook 2010.

只是尝试按照Arioch的建议将我的表格发送到后台:

Just tried to send my form into background as suggested by Arioch:

SetWindowPos(AWnd, HWND_BOTTOM, 0, 0, 0, 0, SWP_NOMOVE or SWP_NOSIZE);
MailIt.Display(AModal);
SetForegroundWindow(AWnd);

在这种情况下,Outlook成为了前台(如我所需要),但是我的from可能变得不可见(如果还有其他正在运行的应用程序具有打开的窗体),因此它也不能解决问题.顶部应该是处于模式状态的Outlook,我的应用程序位于Outlook旁边.

In this case Outlook became foreground (as i need it), but my from can became invisible (if there are other running apps with opened forms), so it also doesn't solve the problem. It should be Outlook in modal state on the top and my application is next to Outlook.

SetWindowPos(AWnd, HWND_NOTOPMOST, 0, 0, 0, 0, SWP_NOMOVE or SWP_NOSIZE) 

最好使用HWND_BOTTOM,但不能保证Outlook会成为前景.

Better then HWND_BOTTOM, but it is not guaranteed that Outlook became foreground.

编辑2. 基于事件的最终(希望)解决方案(来自Kobik的建议):

EDITED2. Final (hopefully) solution based on events (suggestion from Kobik):

uses
  Vcl.OleServer, Winapi.ActiveX;

Type
  TOutlookMsgForm = class
  private
  protected
    FOutlook: OutlookApplication;
    FMessageSent: Boolean;

    procedure OnOpen(ASender: TObject; var Cancel: WordBool);
    procedure OnSend(ASender: TObject; var Cancel: WordBool);
    function  TryDisplayOutlookMail(const AMailTo, ASubject, ABody: string;
      const AAttachmentFileNames: array of string; AWnd: HWND; AModal: Boolean): boolean;

    property Outlook: OutlookApplication read FOutlook write FOutlook;
    property MessageSent: Boolean read FMessageSent write FMessageSent;
  public
    class function DisplayOutlookMail(const AMailTo, ASubject, ABody: string;
      const AAttachmentFileNames: array of string; AWnd: HWND; AModal: Boolean = True): boolean; static;
  end;

{ TOutlookMsgForm }

procedure TOutlookMsgForm.OnOpen(ASender: TObject; var Cancel: WordBool);
begin
  if (Outlook<>nil) and (Outlook.ActiveWindow<>nil) then
    OleVariant(Outlook.ActiveWindow).Activate;
end;

procedure TOutlookMsgForm.OnSend(ASender: TObject; var Cancel: WordBool);
begin
  Cancel := False;
  MessageSent := True;
end;

function TOutlookMsgForm.TryDisplayOutlookMail(const AMailTo, ASubject, ABody: string;
  const AAttachmentFileNames: array of string; AWnd: HWND; AModal: Boolean): boolean;
var
  MailIt: MailItem;
  Mail: TMailItem;
  i: Integer;
begin
  MessageSent := False;
  try
    OleInitialize(nil);
    try
      Outlook := CoOutlookApplication.Create;
      Mail := nil;
      try
        MailIt := Outlook.CreateItem(olMailItem) as MailItem;
        MailIt.To_ := AMailTo;
        MailIt.Subject := ASubject;
        MailIt.Body := ABody;
        for i := Low(AAttachmentFileNames) to High(AAttachmentFileNames) do
          MailIt.Attachments.Add(AAttachmentFileNames[i], EmptyParam, EmptyParam, EmptyParam);
        Mail := TMailItem.Create(nil);
        Mail.ConnectTo(MailIt);
        Mail.OnOpen := OnOpen;
        Mail.OnSend := OnSend;
        MailIt.Display(AModal);
        if AModal and (AWnd<>0) then
          SetForegroundWindow(AWnd);
        Result := true;
      finally
        FreeandNil(Mail);
        MailIt := nil;
        Outlook := nil;
      end;
    finally
      OleUnInitialize;
    end;
  except
    Result := False;
  end;
end;

因此已解决(尝试#3).谢谢!

So it is solved (try#3). Thanks!

推荐答案

如果您不能将Outlook放在最前面,也许可以通过从辅助线程发布消息来将自己的应用程序推到后面?

If you cannot bring Outlook to the front, maybe you can push your own applicatio nto the back by posting message from an auxiliary thread ?

这篇关于在Outlook中生成新消息并显示为模式的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆