将应用程序(exe 文件)嵌入到另一个 exe 文件中(类似 mozEmbed)

发布于 2024-08-19 03:53:44 字数 315 浏览 8 评论 0原文

我想将 mozilla firefox 嵌入到我的应用程序中,而不使用任何 activex 控件(TWebBrowser 包装器、mozilla ActiveX...)。我尝试使用 TWebBrowser(实际上 bsalsa 的嵌入式 webBrowser 效果更好),但所有版本的 IE 似乎与流行的 javascript 框架和库(JQuery、ExtJS...)的某些功能不兼容。

我的问题是:我可以从我的应用程序中调用 firefox 的 Exe(是否可以使用 DDE 或 OLE),最重要的是使用 TFrame 或类似的东西在我的应用程序中显示它?

等待您的建议 问候,M

I would like to embed mozilla firefox into my application WITHOUT using any activex control (TWebBrowser wrapper, mozilla ActiveX...). I tried using TWebBrowser (actually bsalsa's embedded webBrowser wich is by far better), but all versions of IE seem incompatible with some features of popular javascript framework and libs (JQuery, ExtJS...).

My question is : can I call firefox's Exe from my application (is it possible with DDE or OLE) and above all SHOW IT inside my app using a TFrame or anything similar ?

waiting for your suggestions
Regards, M

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

许仙没带伞 2024-08-26 03:53:44

您需要稍微清理一下代码,并弄清楚如何与 Firefox 进行“对话”。
但这里介绍了如何将任何应用程序嵌入到 Delphi 表单中。

DFM 文件

object frmMain: TfrmMain
  Left = 195
  Top = 154
  Width = 527
  Height = 363
  Caption = 'Containership Test'
  Color = clBtnFace
  Font.Charset = DEFAULT_CHARSET
  Font.Color = clWindowText
  Font.Height = -11
  Font.Name = 'MS Sans Serif'
  Font.Style = []
  OldCreateOrder = False
  DesignSize = (
    519
    329)
  PixelsPerInch = 96
  TextHeight = 13
  object pnlTop: TPanel
    Left = 0
    Top = 0
    Width = 519
    Height = 292
    Align = alTop
    Anchors = [akLeft, akTop, akRight, akBottom]
    BevelInner = bvLowered
    TabOrder = 0
  end
  object btnLoadApp: TButton
    Left = 172
    Top = 297
    Width = 75
    Height = 25
    Anchors = [akLeft, akBottom]
    Caption = 'Load'
    TabOrder = 1
    OnClick = btnLoadAppClick
  end
  object btnKill: TButton
    Left = 260
    Top = 297
    Width = 75
    Height = 25
    Anchors = [akLeft, akBottom]
    Caption = 'Kill'
    TabOrder = 2
    OnClick = btnKillClick
  end
end

main.pas 文件

unit main;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, ExtCtrls, ShellApi;

type
  TfrmMain = class(TForm)
    pnlTop: TPanel;
    btnLoadApp: TButton;
    btnKill: TButton;
    procedure btnLoadAppClick(Sender: TObject);
    procedure btnKillClick(Sender: TObject);
  private
    { Private declarations }
    AppWnd : DWORD;
  public
    { Public declarations }
  end;

var
  frmMain: TfrmMain;

implementation

{$R *.dfm}

procedure TfrmMain.btnLoadAppClick(Sender: TObject);
var
  ExecuteFile : string;
  SEInfo: TShellExecuteInfo;
begin
  ExecuteFile:='c:\Windows\notepad.exe';

  FillChar(SEInfo, SizeOf(SEInfo), 0) ;
  SEInfo.cbSize := SizeOf(TShellExecuteInfo) ;
  with SEInfo do
  begin
    fMask := SEE_MASK_NOCLOSEPROCESS;
    Wnd := pnlTop.Handle;
    lpFile := PChar(ExecuteFile) ;
    nShow := SW_HIDE;
  end;
  if ShellExecuteEx(@SEInfo) then
  begin
    AppWnd := FindWindow(nil, PChar('Untitled - Notepad'));
    if AppWnd <> 0 then
    begin
      Windows.SetParent(AppWnd, SEInfo.Wnd);
      ShowWindow(AppWnd, SW_SHOWMAXIMIZED);
      ShowWindow(AppWnd, SW_SHOWMAXIMIZED);
    end;
  end
  else
    ShowMessage('Error starting notepad!') ;
end;

procedure TfrmMain.btnKillClick(Sender: TObject);
begin
  if (AppWnd <> 0) then
  begin
    PostMessage(AppWnd, WM_Close, 0, 0);
    AppWnd := 0;
  end;
end;

end.

You'll need to clean up the code a bit and work out how you'll "talk" to Firefox.
But here is how you can embed any app inside a Delphi form.

DFM File

object frmMain: TfrmMain
  Left = 195
  Top = 154
  Width = 527
  Height = 363
  Caption = 'Containership Test'
  Color = clBtnFace
  Font.Charset = DEFAULT_CHARSET
  Font.Color = clWindowText
  Font.Height = -11
  Font.Name = 'MS Sans Serif'
  Font.Style = []
  OldCreateOrder = False
  DesignSize = (
    519
    329)
  PixelsPerInch = 96
  TextHeight = 13
  object pnlTop: TPanel
    Left = 0
    Top = 0
    Width = 519
    Height = 292
    Align = alTop
    Anchors = [akLeft, akTop, akRight, akBottom]
    BevelInner = bvLowered
    TabOrder = 0
  end
  object btnLoadApp: TButton
    Left = 172
    Top = 297
    Width = 75
    Height = 25
    Anchors = [akLeft, akBottom]
    Caption = 'Load'
    TabOrder = 1
    OnClick = btnLoadAppClick
  end
  object btnKill: TButton
    Left = 260
    Top = 297
    Width = 75
    Height = 25
    Anchors = [akLeft, akBottom]
    Caption = 'Kill'
    TabOrder = 2
    OnClick = btnKillClick
  end
end

main.pas file

unit main;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, ExtCtrls, ShellApi;

type
  TfrmMain = class(TForm)
    pnlTop: TPanel;
    btnLoadApp: TButton;
    btnKill: TButton;
    procedure btnLoadAppClick(Sender: TObject);
    procedure btnKillClick(Sender: TObject);
  private
    { Private declarations }
    AppWnd : DWORD;
  public
    { Public declarations }
  end;

var
  frmMain: TfrmMain;

implementation

{$R *.dfm}

procedure TfrmMain.btnLoadAppClick(Sender: TObject);
var
  ExecuteFile : string;
  SEInfo: TShellExecuteInfo;
begin
  ExecuteFile:='c:\Windows\notepad.exe';

  FillChar(SEInfo, SizeOf(SEInfo), 0) ;
  SEInfo.cbSize := SizeOf(TShellExecuteInfo) ;
  with SEInfo do
  begin
    fMask := SEE_MASK_NOCLOSEPROCESS;
    Wnd := pnlTop.Handle;
    lpFile := PChar(ExecuteFile) ;
    nShow := SW_HIDE;
  end;
  if ShellExecuteEx(@SEInfo) then
  begin
    AppWnd := FindWindow(nil, PChar('Untitled - Notepad'));
    if AppWnd <> 0 then
    begin
      Windows.SetParent(AppWnd, SEInfo.Wnd);
      ShowWindow(AppWnd, SW_SHOWMAXIMIZED);
      ShowWindow(AppWnd, SW_SHOWMAXIMIZED);
    end;
  end
  else
    ShowMessage('Error starting notepad!') ;
end;

procedure TfrmMain.btnKillClick(Sender: TObject);
begin
  if (AppWnd <> 0) then
  begin
    PostMessage(AppWnd, WM_Close, 0, 0);
    AppWnd := 0;
  end;
end;

end.
深海蓝天 2024-08-26 03:53:44

您可以将 DLL 嵌入到您的应用程序中并“加载”,然后使用 BTMemoryModule.pas(只需 google 即可找到)。

如果这个 DLL 是一个 COM 对象,它可能会“加载”COM DLL 工厂并获取所需的 COM 接口的实例:

var
    // Our own method of COM / OLE object loading!
    Lib:       HMODULE;
    Ptr:       TDllGetClassObject;
    Unl:       TDLLCanUnloadNow;
    I:         IClassFactory;
initialization
    Lib := LoadLibrary( 'zkemkeeper.dll' );
    Ptr := GetProcAddress( Lib, 'DllGetClassObject' );
    Unl := GetProcAddress( Lib, 'DllCanUnloadNow' );
    if Assigned( Ptr ) and ( Ptr( CLASS_CZKEM, IClassFactory, I ) <> S_OK ) then I := nil;
finalization
    I := nil;

OleInitialize( nil );
// Create a IZKEM interface instance
if not Assigned( I ) then Exit;
if I.CreateInstance( nil, IZKEM, CZ ) <> S_OK then Exit;
if not Assigned( CZ ) then Exit;

我不知道如何嵌入可执行文件。

我希望这些信息有帮助。

You can embed DLLs into your application and "load" then using BTMemoryModule.pas (just google it and you find it).

If this DLL is a COM object it might work to "load" the COM DLL factory and obtaining an instance of the COM interface you want:

var
    // Our own method of COM / OLE object loading!
    Lib:       HMODULE;
    Ptr:       TDllGetClassObject;
    Unl:       TDLLCanUnloadNow;
    I:         IClassFactory;
initialization
    Lib := LoadLibrary( 'zkemkeeper.dll' );
    Ptr := GetProcAddress( Lib, 'DllGetClassObject' );
    Unl := GetProcAddress( Lib, 'DllCanUnloadNow' );
    if Assigned( Ptr ) and ( Ptr( CLASS_CZKEM, IClassFactory, I ) <> S_OK ) then I := nil;
finalization
    I := nil;

OleInitialize( nil );
// Create a IZKEM interface instance
if not Assigned( I ) then Exit;
if I.CreateInstance( nil, IZKEM, CZ ) <> S_OK then Exit;
if not Assigned( CZ ) then Exit;

I do not know how to embed executables.

I hope this info helps.

黑白记忆 2024-08-26 03:53:44

将 EXE 嵌入应用程序的最简单方法是将其添加为资源。

使用类似以下文本的内容创建一个 .RC 文件:

OTHER_EXE_FILE  RCDATA "nameofother.exe"

然后使用 brcc32.exe,您可以编译一个与 .RC 同名的 .RES 文件,然后您可以使用该文件在您的应用程序中包含 ($I) 新的 .RES 文件。 NAMEOFOTHER.EXE 必须与 .RC 文件位于同一文件夹中,或者路径正确,IIRC。

据说还有另一种方法可以做到这一点。
您不使用命令行 brcc32.exe 编译器,只需将 .RC 文件包含 ($I) 到您的程序中,编译器就会动态编译 .RC 文件。

无法告诉你第二种方法是否有效,因为我从未尝试过。

The simplest way to embed an EXE into your application is to add it as a resource.

Make a .RC file with something like the following text:

OTHER_EXE_FILE  RCDATA "nameofother.exe"

then using brcc32.exe you can compile a .RES file of the same name as the .RC with which you can then include ($I) the new .RES file in your application. The NAMEOFOTHER.EXE has to be in the same folder as the .RC file or be properly pathed, IIRC.

There is supposededly another way of doing this as well.
You don't use the command line brcc32.exe compiler and just include ($I) the .RC file into your program and the compiler the compiles the .RC file on the fly.

Can't tell you if the second method works or not as I've never tried it.

听不够的曲调 2024-08-26 03:53:44

我认为最初的人真正想要的是一个作为控件嵌入到他的应用程序中的 Web 浏览器渲染引擎。如果是这样,Gecko(mozilla 渲染部分)可以作为您的应用程序的插件。我认为你不想运行 EXE。

例如,Mozilla Firefox 不仅仅是一个 EXE 文件,还需要其他东西,包括配置文件文件夹。您可能还没有考虑到可能导致的所有问题。

如果您只想要一个网络浏览器控件,这不是方法。试试这个:
http://ftp.newbielabs.com/Delphi%20Gecko%20SDK/
https://sourceforge.net/projects/d-gecko/

I think what the original guy actually wants is a Web browser rendering engine embedded as a control in his application. If so, Gecko (The mozilla rendering part) is available as a plugin for your Application. I don't think you want to run an EXE.

For example, Mozilla Firefox isn't just an EXE file, but requires other stuff including a profiles folder. YOu probably haven't thought about all the problems that would cause.

If you just want a web browser control, this is not the way to do it. Try this instead:
http://ftp.newbielabs.com/Delphi%20Gecko%20SDK/
https://sourceforge.net/projects/d-gecko/

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文