CEF4Delphi 手柄打开选项卡(并下载文件)

CEF4Delphi Handle Opening a Tab (and Download a File)

提问人:Robbie Matthews 提问时间:5/27/2021 更新时间:5/28/2021 访问量:1142

问:

我在处理 Chromium 中的下载链接时遇到了特别的问题。

问题不在于下载(这里回答得很好:CEF4 Chromium Delphi 10.2 Tokyo - 如何处理下载对话? ...但是这个特定的链接被标记为 target=“_blank”。

这会触发 OnBeforePopup,targetDisposition=WOD_NEW_FOREGROUND_TAB 但是,在几乎所有示例代码中,OnBeforePopup 处理程序都具有以下代码:

  // For simplicity, this demo blocks all popup windows and new tabs
  Result := (targetDisposition in [WOD_NEW_FOREGROUND_TAB, WOD_NEW_BACKGROUND_TAB, WOD_NEW_POPUP, WOD_NEW_WINDOW]);

这有效地阻止了该链接的继续,因此永远不会触发 OnBeforeDownload 事件。

如果我注释掉弹出窗口阻止程序,默认行为似乎是打开一个新的空白窗口,然后按预期继续下载事件。 但是,下载永远不会完全完成(它会达到 100% 但永远不会“完成”),并且新窗口永远不会消失。

我的问题分为两部分:

  1. 我能否获得有关如何在 OnBeforePopup 事件中创建我有权控制的新浏览器窗口的一些指导?
  2. 如何正确完成下载?

注意:如果我将下载文件的实际 targetURL 粘贴到地址栏中,下载会非常愉快地完成,所以我怀疑关键在于处理默认窗口。

注意:我找到了 CEF API 文档,它的信息量不是很大。

注意:我知道 TabBrowser2 处理弹出窗口拦截,但还不清楚发生了什么,显然是调用客户端窗口然后调用主窗口,主窗口又再次调用客户端窗口。另外,到目前为止,我所拥有的结构并不适合该解决方案。 这

德尔福 铬嵌入式 CEF4Delphi

评论


答:

1赞 Robbie Matthews 5/28/2021 #1

部分答案:PopupBrowser 演示更清楚地显示了它。至少 部分记录了正在发生的事情。

从评论:

// VCL components *MUST* be created and destroyed in the main thread but CEF executes the
// TChromium.OnBeforePopup in a different thread.

// For this reason this demo creates a hidden popup form (TChildForm) in case CEF needs to show a popup window.
// TChromium.OnBeforePopup calls TChildForm.CreateClientHandler to initialize some parameters and create the new ICefClient.
// After that, it sends a CEF_CREATENEXTCHILD message to show the popup form and create a new one.

这相当清楚地解释了正在发生的事情。

CreateClientHandler(var aClient : ICefClient...

填充在 BeforePopup 调用中传递的 clienthandler 参数。

1赞 Maico_Delphi 5/28/2021 #2

您可以使用事件 ChromiumBeforePopup 打开新选项卡

procedure ChromiumBeforePopup(Sender: TObject; const browser: ICefBrowser;
  const frame: ICefFrame; const targetUrl, targetFrameName: ustring;
  targetDisposition: TCefWindowOpenDisposition; userGesture: Boolean;
  const popupFeatures: TCefPopupFeatures; var windowInfo: TCefWindowInfo; var client: ICefClient;
  var settings: TCefBrowserSettings; var extra_info: ICefDictionaryValue; var noJavascriptAccess,
  Result: Boolean);
begin
  Result := not(CreateClientHandler(windowInfo, client, targetFrameName, popupFeatures));
end;