Create a ChromeBrowserHostImpl for every Chrome tab (see issue #2969)

The Browser object represents the top-level Chrome browser window. One or more
tabs (WebContents) are then owned by the Browser object via TabStripModel. A
new Browser object can be created programmatically using "new Browser" or
Browser::Create, or as a result of user action such as dragging a tab out of an
existing window. New or existing tabs can also be added to an already existing
Browser object.

The Browser object acts as the WebContentsDelegate for all attached tabs. CEF
integration requires WebContentsDelegate callbacks and notification of tab
attach/detach. To support this integration we add a cef::BrowserDelegate
(ChromeBrowserDelegate) member that is created in the Browser constructor and
receives delegation for the Browser callbacks. ChromeBrowserDelegate creates a
new ChromeBrowserHostImpl when a tab is added to a Browser for the first time,
and that ChromeBrowserHostImpl continues to exist until the tab's WebContents
is destroyed. The associated WebContents object does not change, but the
Browser object will change when the tab is dragged between windows.

CEF callback logic is shared between the chrome and alloy runtimes where
possible. This shared logic has been extracted from CefBrowserHostImpl to
create new CefBrowserHostBase and CefBrowserContentsDelegate classes. The
CefBrowserHostImpl class is now only used with the alloy runtime and will be
renamed to AlloyBrowserHostImpl in a future commit.
This commit is contained in:
Marshall Greenblatt
2020-09-17 18:24:08 -04:00
parent 7ca9e9c54b
commit 38d8acfa18
52 changed files with 3138 additions and 1603 deletions

View File

@ -423,10 +423,15 @@ static_library("libcef_static") {
"libcef/browser/alloy/alloy_content_browser_client.h",
"libcef/browser/audio_capturer.cc",
"libcef/browser/audio_capturer.h",
"libcef/browser/browser_contents_delegate.cc",
"libcef/browser/browser_contents_delegate.h",
"libcef/browser/browser_context.cc",
"libcef/browser/browser_context.h",
"libcef/browser/browser_context_keyed_service_factories.cc",
"libcef/browser/browser_context_keyed_service_factories.h",
"libcef/browser/browser_host_base.cc",
"libcef/browser/browser_host_base.h",
"libcef/browser/browser_host_create.cc",
"libcef/browser/browser_host_impl.cc",
"libcef/browser/browser_host_impl.h",
"libcef/browser/browser_info.cc",
@ -442,10 +447,13 @@ static_library("libcef_static") {
"libcef/browser/browser_platform_delegate_create.cc",
"libcef/browser/browser_util.cc",
"libcef/browser/browser_util.h",
"libcef/browser/chrome/browser_platform_delegate_chrome.cc",
"libcef/browser/chrome/browser_platform_delegate_chrome.h",
"libcef/browser/chrome/browser_delegate.h",
"libcef/browser/chrome/chrome_browser_context.cc",
"libcef/browser/chrome/chrome_browser_context.h",
"libcef/browser/chrome/chrome_browser_delegate.cc",
"libcef/browser/chrome/chrome_browser_delegate.h",
"libcef/browser/chrome/chrome_browser_host_impl.cc",
"libcef/browser/chrome/chrome_browser_host_impl.h",
"libcef/browser/chrome/chrome_browser_main_extra_parts_cef.cc",
"libcef/browser/chrome/chrome_browser_main_extra_parts_cef.h",
"libcef/browser/chrome/chrome_content_browser_client_cef.cc",

View File

@ -33,7 +33,7 @@
// by hand. See the translator.README.txt file in the tools directory for
// more information.
//
// $hash=306236316b35037523ca566068d133755bce48fd$
// $hash=17e60bfb954ddf6c40b90b9a117d90a0fe3f08d6$
//
#ifndef CEF_INCLUDE_CAPI_CEF_BROWSER_PROCESS_HANDLER_CAPI_H_
@ -41,6 +41,7 @@
#pragma once
#include "include/capi/cef_base_capi.h"
#include "include/capi/cef_client_capi.h"
#include "include/capi/cef_command_line_capi.h"
#include "include/capi/cef_print_handler_capi.h"
#include "include/capi/cef_values_capi.h"
@ -101,6 +102,16 @@ typedef struct _cef_browser_process_handler_t {
void(CEF_CALLBACK* on_schedule_message_pump_work)(
struct _cef_browser_process_handler_t* self,
int64 delay_ms);
///
// Return the default client for use with a newly created browser window. If
// null is returned the browser will be unmanaged (no callbacks will be
// executed for that browser) and application shutdown will be blocked until
// the browser window is closed manually. This function is currently only used
// with the chrome runtime.
///
struct _cef_client_t*(CEF_CALLBACK* get_default_client)(
struct _cef_browser_process_handler_t* self);
} cef_browser_process_handler_t;
#ifdef __cplusplus

View File

@ -42,13 +42,13 @@
// way that may cause binary incompatibility with other builds. The universal
// hash value will change if any platform is affected whereas the platform hash
// values will change only if that particular platform is affected.
#define CEF_API_HASH_UNIVERSAL "09d3d4f08869644fe3baa7a751de537f3446525b"
#define CEF_API_HASH_UNIVERSAL "c148b1a4fd1d29c2e14b1ab8ce1c04f29013de73"
#if defined(OS_WIN)
#define CEF_API_HASH_PLATFORM "3022db6736af26cc38158d38e22f74a51312a5c9"
#define CEF_API_HASH_PLATFORM "1f380ef6bde94cd7331d090b7aee0a08f2515541"
#elif defined(OS_MAC)
#define CEF_API_HASH_PLATFORM "13e2e2451c2320f0d16b35ba53b3295409888dd8"
#define CEF_API_HASH_PLATFORM "c42f0866e58d3f96183e1f8931a4d01a7900b0b4"
#elif defined(OS_LINUX)
#define CEF_API_HASH_PLATFORM "d781b815150795b0bce95d72ce967b508c9a04d5"
#define CEF_API_HASH_PLATFORM "92824ced77603246263f1f2ecf95ff4fad73885d"
#endif
#ifdef __cplusplus

View File

@ -39,6 +39,7 @@
#pragma once
#include "include/cef_base.h"
#include "include/cef_client.h"
#include "include/cef_command_line.h"
#include "include/cef_print_handler.h"
#include "include/cef_values.h"
@ -90,6 +91,16 @@ class CefBrowserProcessHandler : public virtual CefBaseRefCounted {
///
/*--cef()--*/
virtual void OnScheduleMessagePumpWork(int64 delay_ms) {}
///
// Return the default client for use with a newly created browser window. If
// null is returned the browser will be unmanaged (no callbacks will be
// executed for that browser) and application shutdown will be blocked until
// the browser window is closed manually. This method is currently only used
// with the chrome runtime.
///
/*--cef()--*/
virtual CefRefPtr<CefClient> GetDefaultClient() { return nullptr; }
};
#endif // CEF_INCLUDE_CEF_BROWSER_PROCESS_HANDLER_H_

View File

@ -285,10 +285,6 @@ bool AlloyBrowserContext::IsPrintPreviewSupported() const {
return !GetPrefs()->GetBoolean(prefs::kPrintPreviewDisabled);
}
void AlloyBrowserContext::AddVisitedURLs(const std::vector<GURL>& urls) {
visitedlink_master_->AddURLs(urls);
}
content::ResourceContext* AlloyBrowserContext::GetResourceContext() {
if (!resource_context_) {
resource_context_ = std::make_unique<content::ResourceContext>();
@ -454,3 +450,7 @@ DownloadPrefs* AlloyBrowserContext::GetDownloadPrefs() {
}
return download_prefs_.get();
}
void AlloyBrowserContext::AddVisitedURLs(const std::vector<GURL>& urls) {
visitedlink_master_->AddURLs(urls);
}

View File

@ -53,7 +53,6 @@ class AlloyBrowserContext : public ChromeProfileAlloy,
CefRefPtr<CefExtension> GetExtension(const CefString& extension_id) override;
bool UnloadExtension(const CefString& extension_id) override;
bool IsPrintPreviewSupported() const override;
void AddVisitedURLs(const std::vector<GURL>& urls) override;
// content::BrowserContext overrides.
content::ResourceContext* GetResourceContext() override;
@ -116,6 +115,10 @@ class AlloyBrowserContext : public ChromeProfileAlloy,
return extension_system_;
}
// Called from CefBrowserHostImpl::DidFinishNavigation to update the table of
// visited links.
void AddVisitedURLs(const std::vector<GURL>& urls);
// Called from DownloadPrefs::FromBrowserContext.
DownloadPrefs* GetDownloadPrefs();

View File

@ -495,8 +495,7 @@ bool NavigationOnUIThread(
// Initiating a new navigation in OnBeforeBrowse will delete the
// InterceptNavigationThrottle that currently owns this callback,
// resulting in a crash. Use the lock to prevent that.
std::unique_ptr<CefBrowserHostImpl::NavigationLock> navigation_lock =
browser->CreateNavigationLock();
auto navigation_lock = browser->browser_info()->CreateNavigationLock();
ignore_navigation = handler->OnBeforeBrowse(
browser.get(), frame, request.get(), params.has_user_gesture(),
params.is_redirect());

View File

@ -28,7 +28,7 @@ CefBrowserPlatformDelegateAlloy::CefBrowserPlatformDelegateAlloy()
: weak_ptr_factory_(this) {}
content::WebContents* CefBrowserPlatformDelegateAlloy::CreateWebContents(
CefBrowserHostImpl::CreateParams& create_params,
CefBrowserHostBase::CreateParams& create_params,
bool& own_web_contents) {
// Get or create the request context and browser context.
CefRefPtr<CefRequestContextImpl> request_context_impl =

View File

@ -15,7 +15,7 @@
class CefBrowserPlatformDelegateAlloy : public CefBrowserPlatformDelegate {
public:
content::WebContents* CreateWebContents(
CefBrowserHostImpl::CreateParams& create_params,
CefBrowserHostBase::CreateParams& create_params,
bool& own_web_contents) override;
void WebContentsCreated(content::WebContents* web_contents,
bool owned) override;

View File

@ -0,0 +1,450 @@
// Copyright 2020 The Chromium Embedded Framework Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "libcef/browser/browser_contents_delegate.h"
#include "libcef/browser/browser_host_base.h"
#include "content/public/browser/navigation_entry.h"
#include "content/public/browser/navigation_handle.h"
#include "content/public/browser/render_view_host.h"
CefBrowserContentsDelegate::CefBrowserContentsDelegate(
scoped_refptr<CefBrowserInfo> browser_info)
: browser_info_(browser_info) {
DCHECK(browser_info_->browser());
}
void CefBrowserContentsDelegate::ObserveWebContents(
content::WebContents* new_contents) {
Observe(new_contents);
if (new_contents) {
// Create the frame representation before OnAfterCreated is called for a new
// browser. Additionally, RenderFrameCreated is otherwise not called at all
// for new popup browsers.
RenderFrameCreated(new_contents->GetMainFrame());
}
}
void CefBrowserContentsDelegate::AddObserver(Observer* observer) {
observers_.AddObserver(observer);
}
void CefBrowserContentsDelegate::RemoveObserver(Observer* observer) {
observers_.RemoveObserver(observer);
}
void CefBrowserContentsDelegate::LoadingStateChanged(
content::WebContents* source,
bool to_different_document) {
const int current_index =
source->GetController().GetLastCommittedEntryIndex();
const int max_index = source->GetController().GetEntryCount() - 1;
const bool is_loading = source->IsLoading();
const bool can_go_back = (current_index > 0);
const bool can_go_forward = (current_index < max_index);
// This method may be called multiple times in a row with |is_loading|
// true as a result of https://crrev.com/5e750ad0. Ignore the 2nd+ times.
if (is_loading_ == is_loading && can_go_back_ == can_go_back &&
can_go_forward_ == can_go_forward) {
return;
}
is_loading_ = is_loading;
can_go_back_ = can_go_back;
can_go_forward_ = can_go_forward;
OnStateChanged(State::kNavigation);
if (auto c = client()) {
if (auto handler = c->GetLoadHandler()) {
handler->OnLoadingStateChange(browser(), is_loading, can_go_back,
can_go_forward);
}
}
}
void CefBrowserContentsDelegate::UpdateTargetURL(content::WebContents* source,
const GURL& url) {
if (auto c = client()) {
if (auto handler = c->GetDisplayHandler()) {
handler->OnStatusMessage(browser(), url.spec());
}
}
}
bool CefBrowserContentsDelegate::DidAddMessageToConsole(
content::WebContents* source,
blink::mojom::ConsoleMessageLevel log_level,
const base::string16& message,
int32_t line_no,
const base::string16& source_id) {
if (auto c = client()) {
if (auto handler = c->GetDisplayHandler()) {
// Use LOGSEVERITY_DEBUG for unrecognized |level| values.
cef_log_severity_t cef_level = LOGSEVERITY_DEBUG;
switch (log_level) {
case blink::mojom::ConsoleMessageLevel::kVerbose:
cef_level = LOGSEVERITY_DEBUG;
break;
case blink::mojom::ConsoleMessageLevel::kInfo:
cef_level = LOGSEVERITY_INFO;
break;
case blink::mojom::ConsoleMessageLevel::kWarning:
cef_level = LOGSEVERITY_WARNING;
break;
case blink::mojom::ConsoleMessageLevel::kError:
cef_level = LOGSEVERITY_ERROR;
break;
}
return handler->OnConsoleMessage(browser(), cef_level, message, source_id,
line_no);
}
}
return false;
}
void CefBrowserContentsDelegate::DidNavigateMainFramePostCommit(
content::WebContents* web_contents) {
has_document_ = false;
OnStateChanged(State::kDocument);
}
void CefBrowserContentsDelegate::EnterFullscreenModeForTab(
content::RenderFrameHost* requesting_frame,
const blink::mojom::FullscreenOptions& options) {
OnFullscreenModeChange(/*fullscreen=*/true);
}
void CefBrowserContentsDelegate::ExitFullscreenModeForTab(
content::WebContents* web_contents) {
OnFullscreenModeChange(/*fullscreen=*/false);
}
void CefBrowserContentsDelegate::RenderFrameCreated(
content::RenderFrameHost* render_frame_host) {
browser_info_->MaybeCreateFrame(render_frame_host, false /* is_guest_view */);
}
void CefBrowserContentsDelegate::RenderFrameHostChanged(
content::RenderFrameHost* old_host,
content::RenderFrameHost* new_host) {
// Just in case RenderFrameCreated wasn't called for some reason.
RenderFrameCreated(new_host);
}
void CefBrowserContentsDelegate::RenderFrameDeleted(
content::RenderFrameHost* render_frame_host) {
const auto frame_id = CefFrameHostImpl::MakeFrameId(render_frame_host);
browser_info_->RemoveFrame(render_frame_host);
if (focused_frame_ && focused_frame_->GetIdentifier() == frame_id) {
focused_frame_ = nullptr;
OnStateChanged(State::kFocusedFrame);
}
}
void CefBrowserContentsDelegate::RenderViewReady() {
if (auto c = client()) {
if (auto handler = c->GetRequestHandler()) {
handler->OnRenderViewReady(browser());
}
}
}
void CefBrowserContentsDelegate::RenderProcessGone(
base::TerminationStatus status) {
cef_termination_status_t ts = TS_ABNORMAL_TERMINATION;
if (status == base::TERMINATION_STATUS_PROCESS_WAS_KILLED)
ts = TS_PROCESS_WAS_KILLED;
else if (status == base::TERMINATION_STATUS_PROCESS_CRASHED)
ts = TS_PROCESS_CRASHED;
else if (status == base::TERMINATION_STATUS_OOM)
ts = TS_PROCESS_OOM;
else if (status != base::TERMINATION_STATUS_ABNORMAL_TERMINATION)
return;
if (auto c = client()) {
if (auto handler = c->GetRequestHandler()) {
auto navigation_lock = browser_info_->CreateNavigationLock();
handler->OnRenderProcessTerminated(browser(), ts);
}
}
}
void CefBrowserContentsDelegate::OnFrameFocused(
content::RenderFrameHost* render_frame_host) {
CefRefPtr<CefFrameHostImpl> frame = static_cast<CefFrameHostImpl*>(
browser_info_->GetFrameForHost(render_frame_host).get());
if (!frame || frame->IsFocused())
return;
CefRefPtr<CefFrameHostImpl> previous_frame = focused_frame_;
if (frame->IsMain())
focused_frame_ = nullptr;
else
focused_frame_ = frame;
if (!previous_frame) {
// The main frame is focused by default.
previous_frame = browser_info_->GetMainFrame();
}
if (previous_frame->GetIdentifier() != frame->GetIdentifier()) {
previous_frame->SetFocused(false);
frame->SetFocused(true);
}
OnStateChanged(State::kFocusedFrame);
}
void CefBrowserContentsDelegate::DocumentAvailableInMainFrame() {
has_document_ = true;
OnStateChanged(State::kDocument);
if (auto c = client()) {
if (auto handler = c->GetRequestHandler()) {
handler->OnDocumentAvailableInMainFrame(browser());
}
}
}
void CefBrowserContentsDelegate::LoadProgressChanged(double progress) {
if (auto c = client()) {
if (auto handler = c->GetDisplayHandler()) {
handler->OnLoadingProgressChange(browser(), progress);
}
}
}
void CefBrowserContentsDelegate::DidStopLoading() {
// Notify all renderers that loading has stopped. We used to use
// RenderFrameObserver::DidStopLoading in the renderer process but that was
// removed in https://crrev.com/3e37dd0ead. However, that callback wasn't
// necessarily accurate because it wasn't called in all of the cases where
// RenderFrameImpl sends the FrameHostMsg_DidStopLoading message. This adds
// an additional round trip but should provide the same or improved
// functionality.
for (const auto& frame : browser_info_->GetAllFrames()) {
frame->MaybeSendDidStopLoading();
}
}
void CefBrowserContentsDelegate::DidFinishNavigation(
content::NavigationHandle* navigation_handle) {
const net::Error error_code = navigation_handle->GetNetErrorCode();
// Skip calls where the navigation has not yet committed and there is no
// error code. For example, when creating a browser without loading a URL.
if (!navigation_handle->HasCommitted() && error_code == net::OK)
return;
const bool is_main_frame = navigation_handle->IsInMainFrame();
const GURL& url =
(error_code == net::OK ? navigation_handle->GetURL() : GURL());
auto browser_info = browser_info_;
// May return NULL when starting a new navigation if the previous navigation
// caused the renderer process to crash during load.
CefRefPtr<CefFrameHostImpl> frame = browser_info->GetFrameForFrameTreeNode(
navigation_handle->GetFrameTreeNodeId());
if (!frame) {
if (is_main_frame) {
frame = browser_info->GetMainFrame();
} else {
frame =
browser_info->CreateTempSubFrame(CefFrameHostImpl::kInvalidFrameId);
}
}
frame->RefreshAttributes();
if (error_code == net::OK) {
// The navigation has been committed and there is no error.
DCHECK(navigation_handle->HasCommitted());
// Don't call OnLoadStart for same page navigations (fragments,
// history state).
if (!navigation_handle->IsSameDocument()) {
OnLoadStart(frame.get(), navigation_handle->GetPageTransition());
}
if (is_main_frame) {
OnAddressChange(url);
}
} else {
// The navigation failed with an error. This may happen before commit
// (e.g. network error) or after commit (e.g. response filter error).
// If the error happened before commit then this call will originate from
// RenderFrameHostImpl::OnDidFailProvisionalLoadWithError.
// OnLoadStart/OnLoadEnd will not be called.
OnLoadError(frame.get(), navigation_handle->GetURL(), error_code);
}
}
void CefBrowserContentsDelegate::DidFailLoad(
content::RenderFrameHost* render_frame_host,
const GURL& validated_url,
int error_code) {
// The navigation failed after commit. OnLoadStart was called so we also
// call OnLoadEnd.
auto frame = browser_info_->GetFrameForHost(render_frame_host);
frame->RefreshAttributes();
OnLoadError(frame, validated_url, error_code);
OnLoadEnd(frame, validated_url, error_code);
}
bool CefBrowserContentsDelegate::OnMessageReceived(
const IPC::Message& message,
content::RenderFrameHost* render_frame_host) {
// Messages may arrive after a frame is detached. Ignore those messages.
auto frame = browser_info_->GetFrameForHost(render_frame_host);
if (frame) {
return static_cast<CefFrameHostImpl*>(frame.get())
->OnMessageReceived(message);
}
return false;
}
void CefBrowserContentsDelegate::TitleWasSet(content::NavigationEntry* entry) {
// |entry| may be NULL if a popup is created via window.open and never
// navigated.
if (entry)
OnTitleChange(entry->GetTitle());
else if (web_contents())
OnTitleChange(web_contents()->GetTitle());
}
void CefBrowserContentsDelegate::PluginCrashed(
const base::FilePath& plugin_path,
base::ProcessId plugin_pid) {
if (auto c = client()) {
if (auto handler = c->GetRequestHandler()) {
handler->OnPluginCrashed(browser(), plugin_path.value());
}
}
}
void CefBrowserContentsDelegate::DidUpdateFaviconURL(
content::RenderFrameHost* render_frame_host,
const std::vector<blink::mojom::FaviconURLPtr>& candidates) {
if (auto c = client()) {
if (auto handler = c->GetDisplayHandler()) {
std::vector<CefString> icon_urls;
for (const auto& icon : candidates) {
if (icon->icon_type == blink::mojom::FaviconIconType::kFavicon) {
icon_urls.push_back(icon->icon_url.spec());
}
}
if (!icon_urls.empty()) {
handler->OnFaviconURLChange(browser(), icon_urls);
}
}
}
}
void CefBrowserContentsDelegate::OnWebContentsFocused(
content::RenderWidgetHost* render_widget_host) {
if (auto c = client()) {
if (auto handler = c->GetFocusHandler()) {
handler->OnGotFocus(browser());
}
}
}
void CefBrowserContentsDelegate::WebContentsDestroyed() {
ObserveWebContents(nullptr);
for (auto& observer : observers_) {
observer.OnWebContentsDestroyed();
}
}
void CefBrowserContentsDelegate::OnAddressChange(const GURL& url) {
if (auto c = client()) {
if (auto handler = c->GetDisplayHandler()) {
// On the handler of an address change.
handler->OnAddressChange(browser(), browser_info_->GetMainFrame(),
url.spec());
}
}
}
void CefBrowserContentsDelegate::OnLoadStart(
CefRefPtr<CefFrame> frame,
ui::PageTransition transition_type) {
if (auto c = client()) {
if (auto handler = c->GetLoadHandler()) {
// On the handler that loading has started.
handler->OnLoadStart(browser(), frame,
static_cast<cef_transition_type_t>(transition_type));
}
}
}
void CefBrowserContentsDelegate::OnLoadError(CefRefPtr<CefFrame> frame,
const GURL& url,
int error_code) {
if (auto c = client()) {
if (auto handler = c->GetLoadHandler()) {
auto navigation_lock = browser_info_->CreateNavigationLock();
// On the handler that loading has failed.
handler->OnLoadError(browser(), frame,
static_cast<cef_errorcode_t>(error_code),
net::ErrorToShortString(error_code), url.spec());
}
}
}
void CefBrowserContentsDelegate::OnLoadEnd(CefRefPtr<CefFrame> frame,
const GURL& url,
int http_status_code) {
if (auto c = client()) {
if (auto handler = c->GetLoadHandler()) {
handler->OnLoadEnd(browser(), frame, http_status_code);
}
}
}
void CefBrowserContentsDelegate::OnTitleChange(const base::string16& title) {
if (auto c = client()) {
if (auto handler = c->GetDisplayHandler()) {
handler->OnTitleChange(browser(), title);
}
}
}
CefRefPtr<CefClient> CefBrowserContentsDelegate::client() const {
if (auto b = browser()) {
return b->GetHost()->GetClient();
}
return nullptr;
}
CefRefPtr<CefBrowser> CefBrowserContentsDelegate::browser() const {
return browser_info_->browser();
}
void CefBrowserContentsDelegate::OnFullscreenModeChange(bool fullscreen) {
if (fullscreen == is_fullscreen_)
return;
is_fullscreen_ = fullscreen;
OnStateChanged(State::kFullscreen);
if (auto c = client()) {
if (auto handler = c->GetDisplayHandler()) {
handler->OnFullscreenModeChange(browser(), fullscreen);
}
}
}
void CefBrowserContentsDelegate::OnStateChanged(State state_changed) {
for (auto& observer : observers_) {
observer.OnStateChanged(state_changed);
}
}

View File

@ -0,0 +1,164 @@
// Copyright 2020 The Chromium Embedded Framework Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CEF_LIBCEF_BROWSER_BROWSER_CONTENTS_DELEGATE_H_
#define CEF_LIBCEF_BROWSER_BROWSER_CONTENTS_DELEGATE_H_
#pragma once
#include <memory>
#include "libcef/browser/frame_host_impl.h"
#include "base/observer_list.h"
#include "content/public/browser/web_contents_delegate.h"
#include "content/public/browser/web_contents_observer.h"
class CefBrowser;
class CefBrowserInfo;
class CefClient;
// Flags that represent which states have changed.
enum class CefBrowserContentsState : uint8_t {
kNone = 0,
kNavigation = (1 << 0),
kDocument = (1 << 1),
kFullscreen = (1 << 2),
kFocusedFrame = (1 << 3),
};
constexpr inline CefBrowserContentsState operator&(
CefBrowserContentsState lhs,
CefBrowserContentsState rhs) {
return static_cast<CefBrowserContentsState>(static_cast<int>(lhs) &
static_cast<int>(rhs));
}
constexpr inline CefBrowserContentsState operator|(
CefBrowserContentsState lhs,
CefBrowserContentsState rhs) {
return static_cast<CefBrowserContentsState>(static_cast<int>(lhs) |
static_cast<int>(rhs));
}
// Tracks state and executes client callbacks based on WebContents callbacks.
// Includes functionality that is shared by the alloy and chrome runtimes.
// Only accessed on the UI thread.
class CefBrowserContentsDelegate : public content::WebContentsDelegate,
public content::WebContentsObserver {
public:
using State = CefBrowserContentsState;
// Interface to implement for observers that wish to be informed of changes
// to the delegate. All methods will be called on the UI thread.
class Observer : public base::CheckedObserver {
public:
// Called after state has changed and before the associated CefClient
// callback is executed.
virtual void OnStateChanged(State state_changed) = 0;
// Called when the associated WebContents is destroyed.
virtual void OnWebContentsDestroyed() = 0;
protected:
~Observer() override {}
};
explicit CefBrowserContentsDelegate(
scoped_refptr<CefBrowserInfo> browser_info);
void ObserveWebContents(content::WebContents* new_contents);
// Manage observer objects. The observer must either outlive this object or
// be removed before destruction.
void AddObserver(Observer* observer);
void RemoveObserver(Observer* observer);
// WebContentsDelegate methods:
void LoadingStateChanged(content::WebContents* source,
bool to_different_document) override;
void UpdateTargetURL(content::WebContents* source, const GURL& url) override;
bool DidAddMessageToConsole(content::WebContents* source,
blink::mojom::ConsoleMessageLevel log_level,
const base::string16& message,
int32_t line_no,
const base::string16& source_id) override;
void DidNavigateMainFramePostCommit(
content::WebContents* web_contents) override;
void EnterFullscreenModeForTab(
content::RenderFrameHost* requesting_frame,
const blink::mojom::FullscreenOptions& options) override;
void ExitFullscreenModeForTab(content::WebContents* web_contents) override;
// WebContentsObserver methods:
void RenderFrameCreated(content::RenderFrameHost* render_frame_host) override;
void RenderFrameHostChanged(content::RenderFrameHost* old_host,
content::RenderFrameHost* new_host) override;
void RenderFrameDeleted(content::RenderFrameHost* render_frame_host) override;
void RenderViewReady() override;
void RenderProcessGone(base::TerminationStatus status) override;
void OnFrameFocused(content::RenderFrameHost* render_frame_host) override;
void DocumentAvailableInMainFrame() override;
void LoadProgressChanged(double progress) override;
void DidStopLoading() override;
void DidFinishNavigation(
content::NavigationHandle* navigation_handle) override;
void DidFailLoad(content::RenderFrameHost* render_frame_host,
const GURL& validated_url,
int error_code) override;
bool OnMessageReceived(const IPC::Message& message,
content::RenderFrameHost* render_frame_host) override;
void TitleWasSet(content::NavigationEntry* entry) override;
void PluginCrashed(const base::FilePath& plugin_path,
base::ProcessId plugin_pid) override;
void DidUpdateFaviconURL(
content::RenderFrameHost* render_frame_host,
const std::vector<blink::mojom::FaviconURLPtr>& candidates) override;
void OnWebContentsFocused(
content::RenderWidgetHost* render_widget_host) override;
void WebContentsDestroyed() override;
// Accessors for state information. Changes will be signaled to
// Observer::OnStateChanged.
bool is_loading() const { return is_loading_; }
bool can_go_back() const { return can_go_back_; }
bool can_go_forward() const { return can_go_forward_; }
bool has_document() const { return has_document_; }
bool is_fullscreen() const { return is_fullscreen_; }
CefRefPtr<CefFrameHostImpl> focused_frame() const { return focused_frame_; }
// Helpers for executing client callbacks.
void OnAddressChange(const GURL& url);
void OnLoadStart(CefRefPtr<CefFrame> frame,
ui::PageTransition transition_type);
void OnLoadError(CefRefPtr<CefFrame> frame, const GURL& url, int error_code);
void OnLoadEnd(CefRefPtr<CefFrame> frame,
const GURL& url,
int http_status_code);
void OnTitleChange(const base::string16& title);
private:
CefRefPtr<CefClient> client() const;
CefRefPtr<CefBrowser> browser() const;
void OnFullscreenModeChange(bool fullscreen);
void OnStateChanged(State state_changed);
scoped_refptr<CefBrowserInfo> browser_info_;
bool is_loading_ = false;
bool can_go_back_ = false;
bool can_go_forward_ = false;
bool has_document_ = false;
bool is_fullscreen_ = false;
// The currently focused frame, or nullptr if the main frame is focused.
CefRefPtr<CefFrameHostImpl> focused_frame_;
// Observers that want to be notified of changes to this object.
base::ObserverList<Observer> observers_;
DISALLOW_COPY_AND_ASSIGN(CefBrowserContentsDelegate);
};
#endif // CEF_LIBCEF_BROWSER_BROWSER_CONTENTS_DELEGATE_H_

View File

@ -456,8 +456,6 @@ bool CefBrowserContext::IsPrintPreviewSupported() const {
return true;
}
void CefBrowserContext::AddVisitedURLs(const std::vector<GURL>& urls) {}
network::mojom::NetworkContext* CefBrowserContext::GetNetworkContext() {
CEF_REQUIRE_UIT();
auto browser_context = AsBrowserContext();

View File

@ -188,10 +188,6 @@ class CefBrowserContext {
// Returns true if this context supports print preview.
virtual bool IsPrintPreviewSupported() const;
// Called from CefBrowserHostImpl::DidNavigateAnyFrame to update the table of
// visited links.
virtual void AddVisitedURLs(const std::vector<GURL>& urls);
network::mojom::NetworkContext* GetNetworkContext();
CefMediaRouterManager* GetMediaRouterManager();

View File

@ -0,0 +1,623 @@
// Copyright 2020 The Chromium Embedded Framework Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "libcef/browser/browser_host_base.h"
#include "libcef/browser/browser_info_manager.h"
#include "libcef/browser/image_impl.h"
#include "libcef/browser/navigation_entry_impl.h"
#include "libcef/browser/net/scheme_handler.h"
#include "libcef/browser/thread_util.h"
#include "base/logging.h"
#include "chrome/browser/spellchecker/spellcheck_factory.h"
#include "chrome/browser/spellchecker/spellcheck_service.h"
#include "components/favicon/core/favicon_url.h"
#include "components/spellcheck/common/spellcheck_features.h"
#include "content/public/browser/browser_context.h"
#include "content/public/browser/download_manager.h"
#include "content/public/browser/download_request_utils.h"
#include "content/public/browser/navigation_entry.h"
#include "ui/gfx/image/image_skia.h"
#if defined(OS_MAC)
#include "components/spellcheck/browser/spellcheck_platform.h"
#endif
namespace {
// Associates a CefBrowserHostBase instance with a WebContents. This object will
// be deleted automatically when the WebContents is destroyed.
class WebContentsUserDataAdapter : public base::SupportsUserData::Data {
public:
static void Register(CefRefPtr<CefBrowserHostBase> browser) {
new WebContentsUserDataAdapter(browser);
}
static CefRefPtr<CefBrowserHostBase> Get(
const content::WebContents* web_contents) {
WebContentsUserDataAdapter* adapter =
static_cast<WebContentsUserDataAdapter*>(
web_contents->GetUserData(UserDataKey()));
if (adapter)
return adapter->browser_;
return nullptr;
}
private:
WebContentsUserDataAdapter(CefRefPtr<CefBrowserHostBase> browser)
: browser_(browser) {
auto web_contents = browser->GetWebContents();
DCHECK(web_contents);
web_contents->SetUserData(UserDataKey(), base::WrapUnique(this));
}
static void* UserDataKey() {
// We just need a unique constant. Use the address of a static that
// COMDAT folding won't touch in an optimizing linker.
static int data_key = 0;
return reinterpret_cast<void*>(&data_key);
}
CefRefPtr<CefBrowserHostBase> browser_;
};
} // namespace
// static
CefRefPtr<CefBrowserHostBase> CefBrowserHostBase::GetBrowserForHost(
const content::RenderViewHost* host) {
DCHECK(host);
CEF_REQUIRE_UIT();
content::WebContents* web_contents = content::WebContents::FromRenderViewHost(
const_cast<content::RenderViewHost*>(host));
if (web_contents)
return GetBrowserForContents(web_contents);
return nullptr;
}
// static
CefRefPtr<CefBrowserHostBase> CefBrowserHostBase::GetBrowserForHost(
const content::RenderFrameHost* host) {
DCHECK(host);
CEF_REQUIRE_UIT();
content::WebContents* web_contents =
content::WebContents::FromRenderFrameHost(
const_cast<content::RenderFrameHost*>(host));
if (web_contents)
return GetBrowserForContents(web_contents);
return nullptr;
}
// static
CefRefPtr<CefBrowserHostBase> CefBrowserHostBase::GetBrowserForContents(
const content::WebContents* contents) {
DCHECK(contents);
CEF_REQUIRE_UIT();
return WebContentsUserDataAdapter::Get(contents);
}
// static
CefRefPtr<CefBrowserHostBase> CefBrowserHostBase::GetBrowserForFrameTreeNode(
int frame_tree_node_id) {
// Use the thread-safe approach.
auto info =
CefBrowserInfoManager::GetInstance()->GetBrowserInfoForFrameTreeNode(
frame_tree_node_id);
if (info) {
auto browser = info->browser();
if (!browser) {
LOG(WARNING) << "Found browser id " << info->browser_id()
<< " but no browser object matching frame tree node id "
<< frame_tree_node_id;
}
return browser;
}
return nullptr;
}
// static
CefRefPtr<CefBrowserHostBase> CefBrowserHostBase::GetBrowserForFrameRoute(
int render_process_id,
int render_routing_id) {
if (render_process_id == -1 || render_routing_id == MSG_ROUTING_NONE)
return nullptr;
if (CEF_CURRENTLY_ON_UIT()) {
// Use the non-thread-safe but potentially faster approach.
content::RenderFrameHost* render_frame_host =
content::RenderFrameHost::FromID(render_process_id, render_routing_id);
if (!render_frame_host)
return nullptr;
return GetBrowserForHost(render_frame_host);
} else {
// Use the thread-safe approach.
bool is_guest_view = false;
auto info =
CefBrowserInfoManager::GetInstance()->GetBrowserInfoForFrameRoute(
render_process_id, render_routing_id, &is_guest_view);
if (info && !is_guest_view) {
auto browser = info->browser();
if (!browser) {
LOG(WARNING) << "Found browser id " << info->browser_id()
<< " but no browser object matching frame process id "
<< render_process_id << " and routing id "
<< render_routing_id;
}
return browser;
}
return nullptr;
}
}
CefBrowserHostBase::CefBrowserHostBase(
const CefBrowserSettings& settings,
CefRefPtr<CefClient> client,
scoped_refptr<CefBrowserInfo> browser_info,
CefRefPtr<CefRequestContextImpl> request_context)
: settings_(settings),
client_(client),
browser_info_(browser_info),
request_context_(request_context) {
CEF_REQUIRE_UIT();
DCHECK(!browser_info_->browser().get());
browser_info_->SetBrowser(this);
contents_delegate_ =
std::make_unique<CefBrowserContentsDelegate>(browser_info_);
contents_delegate_->AddObserver(this);
}
void CefBrowserHostBase::InitializeBrowser() {
CEF_REQUIRE_UIT();
// Associate the WebContents with this browser object.
DCHECK(GetWebContents());
WebContentsUserDataAdapter::Register(this);
}
void CefBrowserHostBase::DestroyBrowser() {
CEF_REQUIRE_UIT();
contents_delegate_->RemoveObserver(this);
contents_delegate_->ObserveWebContents(nullptr);
CefBrowserInfoManager::GetInstance()->RemoveBrowserInfo(browser_info_);
browser_info_->SetBrowser(nullptr);
}
CefRefPtr<CefBrowser> CefBrowserHostBase::GetBrowser() {
return this;
}
CefRefPtr<CefClient> CefBrowserHostBase::GetClient() {
return client_;
}
CefRefPtr<CefRequestContext> CefBrowserHostBase::GetRequestContext() {
return request_context_;
}
void CefBrowserHostBase::StartDownload(const CefString& url) {
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT, base::BindOnce(&CefBrowserHostBase::StartDownload, this, url));
return;
}
GURL gurl = GURL(url.ToString());
if (gurl.is_empty() || !gurl.is_valid())
return;
auto web_contents = GetWebContents();
if (!web_contents)
return;
auto browser_context = web_contents->GetBrowserContext();
if (!browser_context)
return;
content::DownloadManager* manager =
content::BrowserContext::GetDownloadManager(browser_context);
if (!manager)
return;
std::unique_ptr<download::DownloadUrlParameters> params(
content::DownloadRequestUtils::CreateDownloadForWebContentsMainFrame(
web_contents, gurl, MISSING_TRAFFIC_ANNOTATION));
manager->DownloadUrl(std::move(params));
}
void CefBrowserHostBase::DownloadImage(
const CefString& image_url,
bool is_favicon,
uint32 max_image_size,
bool bypass_cache,
CefRefPtr<CefDownloadImageCallback> callback) {
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT,
base::BindOnce(&CefBrowserHostBase::DownloadImage, this, image_url,
is_favicon, max_image_size, bypass_cache, callback));
return;
}
if (!callback)
return;
GURL gurl = GURL(image_url.ToString());
if (gurl.is_empty() || !gurl.is_valid())
return;
auto web_contents = GetWebContents();
if (!web_contents)
return;
web_contents->DownloadImage(
gurl, is_favicon, max_image_size,
max_image_size * gfx::ImageSkia::GetMaxSupportedScale(), bypass_cache,
base::BindOnce(
[](uint32 max_image_size,
CefRefPtr<CefDownloadImageCallback> callback, int id,
int http_status_code, const GURL& image_url,
const std::vector<SkBitmap>& bitmaps,
const std::vector<gfx::Size>& sizes) {
CEF_REQUIRE_UIT();
CefRefPtr<CefImageImpl> image_impl;
if (!bitmaps.empty()) {
image_impl = new CefImageImpl();
image_impl->AddBitmaps(max_image_size, bitmaps);
}
callback->OnDownloadImageFinished(
image_url.spec(), http_status_code, image_impl.get());
},
max_image_size, callback));
}
void CefBrowserHostBase::GetNavigationEntries(
CefRefPtr<CefNavigationEntryVisitor> visitor,
bool current_only) {
DCHECK(visitor.get());
if (!visitor.get())
return;
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT, base::BindOnce(&CefBrowserHostBase::GetNavigationEntries, this,
visitor, current_only));
return;
}
auto web_contents = GetWebContents();
if (!web_contents)
return;
content::NavigationController& controller = web_contents->GetController();
const int total = controller.GetEntryCount();
const int current = controller.GetCurrentEntryIndex();
if (current_only) {
// Visit only the current entry.
CefRefPtr<CefNavigationEntryImpl> entry =
new CefNavigationEntryImpl(controller.GetEntryAtIndex(current));
visitor->Visit(entry.get(), true, current, total);
entry->Detach(nullptr);
} else {
// Visit all entries.
bool cont = true;
for (int i = 0; i < total && cont; ++i) {
CefRefPtr<CefNavigationEntryImpl> entry =
new CefNavigationEntryImpl(controller.GetEntryAtIndex(i));
cont = visitor->Visit(entry.get(), (i == current), i, total);
entry->Detach(nullptr);
}
}
}
CefRefPtr<CefNavigationEntry> CefBrowserHostBase::GetVisibleNavigationEntry() {
if (!CEF_CURRENTLY_ON_UIT()) {
NOTREACHED() << "called on invalid thread";
return nullptr;
}
content::NavigationEntry* entry = nullptr;
auto web_contents = GetWebContents();
if (web_contents)
entry = web_contents->GetController().GetVisibleEntry();
if (!entry)
return nullptr;
return new CefNavigationEntryImpl(entry);
}
void CefBrowserHostBase::ReplaceMisspelling(const CefString& word) {
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT,
base::BindOnce(&CefBrowserHostBase::ReplaceMisspelling, this, word));
return;
}
auto web_contents = GetWebContents();
if (web_contents)
web_contents->ReplaceMisspelling(word);
}
void CefBrowserHostBase::AddWordToDictionary(const CefString& word) {
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT,
base::BindOnce(&CefBrowserHostBase::AddWordToDictionary, this, word));
return;
}
auto web_contents = GetWebContents();
if (!web_contents)
return;
SpellcheckService* spellcheck = nullptr;
content::BrowserContext* browser_context = web_contents->GetBrowserContext();
if (browser_context) {
spellcheck = SpellcheckServiceFactory::GetForContext(browser_context);
if (spellcheck)
spellcheck->GetCustomDictionary()->AddWord(word);
}
#if defined(OS_MAC)
if (spellcheck && spellcheck::UseBrowserSpellChecker()) {
spellcheck_platform::AddWord(spellcheck->platform_spell_checker(), word);
}
#endif
}
CefRefPtr<CefBrowserHost> CefBrowserHostBase::GetHost() {
return this;
}
bool CefBrowserHostBase::CanGoBack() {
base::AutoLock lock_scope(state_lock_);
return can_go_back_;
}
bool CefBrowserHostBase::CanGoForward() {
base::AutoLock lock_scope(state_lock_);
return can_go_forward_;
}
bool CefBrowserHostBase::IsLoading() {
base::AutoLock lock_scope(state_lock_);
return is_loading_;
}
int CefBrowserHostBase::GetIdentifier() {
return browser_id();
}
bool CefBrowserHostBase::IsSame(CefRefPtr<CefBrowser> that) {
auto impl = static_cast<CefBrowserHostBase*>(that.get());
return (impl == this);
}
bool CefBrowserHostBase::HasDocument() {
base::AutoLock lock_scope(state_lock_);
return has_document_;
}
bool CefBrowserHostBase::IsPopup() {
return browser_info_->is_popup();
}
CefRefPtr<CefFrame> CefBrowserHostBase::GetMainFrame() {
return GetFrame(CefFrameHostImpl::kMainFrameId);
}
CefRefPtr<CefFrame> CefBrowserHostBase::GetFocusedFrame() {
return GetFrame(CefFrameHostImpl::kFocusedFrameId);
}
CefRefPtr<CefFrame> CefBrowserHostBase::GetFrame(int64 identifier) {
if (identifier == CefFrameHostImpl::kInvalidFrameId) {
return nullptr;
} else if (identifier == CefFrameHostImpl::kMainFrameId) {
return browser_info_->GetMainFrame();
} else if (identifier == CefFrameHostImpl::kFocusedFrameId) {
base::AutoLock lock_scope(state_lock_);
if (!focused_frame_) {
// The main frame is focused by default.
return browser_info_->GetMainFrame();
}
return focused_frame_;
}
return browser_info_->GetFrameForId(identifier);
}
CefRefPtr<CefFrame> CefBrowserHostBase::GetFrame(const CefString& name) {
for (const auto& frame : browser_info_->GetAllFrames()) {
if (frame->GetName() == name)
return frame;
}
return nullptr;
}
size_t CefBrowserHostBase::GetFrameCount() {
return browser_info_->GetAllFrames().size();
}
void CefBrowserHostBase::GetFrameIdentifiers(std::vector<int64>& identifiers) {
if (identifiers.size() > 0)
identifiers.clear();
const auto frames = browser_info_->GetAllFrames();
if (frames.empty())
return;
identifiers.reserve(frames.size());
for (const auto& frame : frames) {
identifiers.push_back(frame->GetIdentifier());
}
}
void CefBrowserHostBase::GetFrameNames(std::vector<CefString>& names) {
if (names.size() > 0)
names.clear();
const auto frames = browser_info_->GetAllFrames();
if (frames.empty())
return;
names.reserve(frames.size());
for (const auto& frame : frames) {
names.push_back(frame->GetName());
}
}
void CefBrowserHostBase::OnStateChanged(CefBrowserContentsState state_changed) {
// Make sure that CefBrowser state is consistent before the associated
// CefClient callback is executed.
base::AutoLock lock_scope(state_lock_);
if ((state_changed & CefBrowserContentsState::kNavigation) ==
CefBrowserContentsState::kNavigation) {
is_loading_ = contents_delegate_->is_loading();
can_go_back_ = contents_delegate_->can_go_back();
can_go_forward_ = contents_delegate_->can_go_forward();
}
if ((state_changed & CefBrowserContentsState::kDocument) ==
CefBrowserContentsState::kDocument) {
has_document_ = contents_delegate_->has_document();
}
if ((state_changed & CefBrowserContentsState::kFullscreen) ==
CefBrowserContentsState::kFullscreen) {
is_fullscreen_ = contents_delegate_->is_fullscreen();
}
if ((state_changed & CefBrowserContentsState::kFocusedFrame) ==
CefBrowserContentsState::kFocusedFrame) {
focused_frame_ = contents_delegate_->focused_frame();
}
}
void CefBrowserHostBase::OnWebContentsDestroyed() {}
CefRefPtr<CefFrame> CefBrowserHostBase::GetFrameForHost(
const content::RenderFrameHost* host) {
CEF_REQUIRE_UIT();
if (!host)
return nullptr;
return browser_info_->GetFrameForHost(host);
}
CefRefPtr<CefFrame> CefBrowserHostBase::GetFrameForFrameTreeNode(
int frame_tree_node_id) {
return browser_info_->GetFrameForFrameTreeNode(frame_tree_node_id, nullptr);
}
void CefBrowserHostBase::AddObserver(Observer* observer) {
CEF_REQUIRE_UIT();
observers_.AddObserver(observer);
}
void CefBrowserHostBase::RemoveObserver(Observer* observer) {
CEF_REQUIRE_UIT();
observers_.RemoveObserver(observer);
}
bool CefBrowserHostBase::HasObserver(Observer* observer) const {
CEF_REQUIRE_UIT();
return observers_.HasObserver(observer);
}
void CefBrowserHostBase::LoadMainFrameURL(const std::string& url,
const content::Referrer& referrer,
ui::PageTransition transition,
const std::string& extra_headers) {
auto callback = base::BindOnce(&CefBrowserHostBase::LoadMainFrameURL, this,
url, referrer, transition, extra_headers);
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(CEF_UIT, std::move(callback));
return;
}
if (browser_info_->IsNavigationLocked(std::move(callback))) {
return;
}
auto web_contents = GetWebContents();
if (web_contents) {
GURL gurl = GURL(url);
if (!gurl.is_valid() && !gurl.has_scheme()) {
// Try to add "http://" at the beginning
std::string new_url = std::string("http://") + url;
gurl = GURL(new_url);
}
if (!gurl.is_valid()) {
LOG(ERROR)
<< "Invalid URL passed to CefBrowserHostImpl::LoadMainFrameURL: "
<< url;
return;
}
web_contents->GetController().LoadURL(gurl, referrer, transition,
extra_headers);
OnSetFocus(FOCUS_SOURCE_NAVIGATION);
}
}
void CefBrowserHostBase::OnDidFinishLoad(CefRefPtr<CefFrameHostImpl> frame,
const GURL& validated_url,
int http_status_code) {
frame->RefreshAttributes();
// Give internal scheme handlers an opportunity to update content.
scheme::DidFinishLoad(frame, validated_url);
contents_delegate_->OnLoadEnd(frame, validated_url, http_status_code);
}
void CefBrowserHostBase::OnAfterCreated() {
CEF_REQUIRE_UIT();
if (client_) {
if (auto handler = client_->GetLifeSpanHandler()) {
handler->OnAfterCreated(this);
}
}
}
void CefBrowserHostBase::OnBeforeClose() {
CEF_REQUIRE_UIT();
if (client_) {
if (auto handler = client_->GetLifeSpanHandler()) {
handler->OnBeforeClose(this);
}
}
}
void CefBrowserHostBase::OnBrowserDestroyed() {
CEF_REQUIRE_UIT();
for (auto& observer : observers_)
observer.OnBrowserDestroyed(this);
}
int CefBrowserHostBase::browser_id() const {
return browser_info_->browser_id();
}
content::WebContents* CefBrowserHostBase::GetWebContents() const {
CEF_REQUIRE_UIT();
return contents_delegate_->web_contents();
}
content::BrowserContext* CefBrowserHostBase::GetBrowserContext() const {
CEF_REQUIRE_UIT();
auto web_contents = GetWebContents();
if (web_contents)
return web_contents->GetBrowserContext();
return nullptr;
}

View File

@ -0,0 +1,240 @@
// Copyright 2020 The Chromium Embedded Framework Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CEF_LIBCEF_BROWSER_BROWSER_HOST_BASE_H_
#define CEF_LIBCEF_BROWSER_BROWSER_HOST_BASE_H_
#pragma once
#include "include/cef_browser.h"
#include "include/cef_client.h"
#include "include/views/cef_browser_view.h"
#include "libcef/browser/browser_contents_delegate.h"
#include "libcef/browser/browser_info.h"
#include "libcef/browser/frame_host_impl.h"
#include "libcef/browser/request_context_impl.h"
#include "base/observer_list.h"
#include "base/synchronization/lock.h"
#include "extensions/common/view_type.h"
namespace extensions {
class Extension;
}
// Base class for CefBrowserHost implementations. Includes functionality that is
// shared by the alloy and chrome runtimes. All methods are thread-safe unless
// otherwise indicated.
class CefBrowserHostBase : public CefBrowserHost,
public CefBrowser,
public CefBrowserContentsDelegate::Observer {
public:
// Parameters that are passed to the runtime-specific Create methods.
struct CreateParams {
CreateParams() {}
// Copy constructor used with the chrome runtime only.
CreateParams(const CreateParams& that) { operator=(that); }
CreateParams& operator=(const CreateParams& that) {
// Not all parameters can be copied.
client = that.client;
url = that.url;
settings = that.settings;
request_context = that.request_context;
extra_info = that.extra_info;
return *this;
}
// Platform-specific window creation info. Will be nullptr when creating a
// views-hosted browser. Currently used with the alloy runtime only.
std::unique_ptr<CefWindowInfo> window_info;
#if defined(USE_AURA)
// The BrowserView that will own a views-hosted browser. Will be nullptr for
// popup browsers (the BrowserView will be created later in that case).
// Currently used with the alloy runtime only.
CefRefPtr<CefBrowserView> browser_view;
#endif
// Client implementation. May be nullptr.
CefRefPtr<CefClient> client;
// Initial URL to load. May be empty. If this is a valid extension URL then
// the browser will be created as an app view extension host.
GURL url;
// Browser settings.
CefBrowserSettings settings;
// Other browser that opened this DevTools browser. Will be nullptr for non-
// DevTools browsers. Currently used with the alloy runtime only.
CefRefPtr<CefBrowserHostBase> devtools_opener;
// Request context to use when creating the browser. If nullptr the global
// request context will be used.
CefRefPtr<CefRequestContext> request_context;
// Extra information that will be passed to
// CefRenderProcessHandler::OnBrowserCreated.
CefRefPtr<CefDictionaryValue> extra_info;
// Used when explicitly creating the browser as an extension host via
// ProcessManager::CreateBackgroundHost. Currently used with the alloy
// runtime only.
const extensions::Extension* extension = nullptr;
extensions::ViewType extension_host_type = extensions::VIEW_TYPE_INVALID;
};
// Interface to implement for observers that wish to be informed of changes
// to the CefBrowserHostBase. All methods will be called on the UI thread.
class Observer : public base::CheckedObserver {
public:
// Called before |browser| is destroyed. Any references to |browser| should
// be cleared when this method is called.
virtual void OnBrowserDestroyed(CefBrowserHostBase* browser) = 0;
protected:
virtual ~Observer() {}
};
// Returns the browser associated with the specified RenderViewHost.
static CefRefPtr<CefBrowserHostBase> GetBrowserForHost(
const content::RenderViewHost* host);
// Returns the browser associated with the specified RenderFrameHost.
static CefRefPtr<CefBrowserHostBase> GetBrowserForHost(
const content::RenderFrameHost* host);
// Returns the browser associated with the specified WebContents.
static CefRefPtr<CefBrowserHostBase> GetBrowserForContents(
const content::WebContents* contents);
// Returns the browser associated with the specified FrameTreeNode ID.
static CefRefPtr<CefBrowserHostBase> GetBrowserForFrameTreeNode(
int frame_tree_node_id);
// Returns the browser associated with the specified frame routing IDs.
static CefRefPtr<CefBrowserHostBase> GetBrowserForFrameRoute(
int render_process_id,
int render_routing_id);
CefBrowserHostBase(const CefBrowserSettings& settings,
CefRefPtr<CefClient> client,
scoped_refptr<CefBrowserInfo> browser_info,
CefRefPtr<CefRequestContextImpl> request_context);
// Called on the UI thread after the associated WebContents is created.
virtual void InitializeBrowser();
// Called on the UI thread after the associated WebContents is destroyed.
// Also called from CefBrowserInfoManager::DestroyAllBrowsers if the browser
// was not properly shut down.
virtual void DestroyBrowser();
// CefBrowserHost methods:
CefRefPtr<CefBrowser> GetBrowser() override;
CefRefPtr<CefClient> GetClient() override;
CefRefPtr<CefRequestContext> GetRequestContext() override;
void StartDownload(const CefString& url) override;
void DownloadImage(const CefString& image_url,
bool is_favicon,
uint32 max_image_size,
bool bypass_cache,
CefRefPtr<CefDownloadImageCallback> callback) override;
void ReplaceMisspelling(const CefString& word) override;
void AddWordToDictionary(const CefString& word) override;
void GetNavigationEntries(CefRefPtr<CefNavigationEntryVisitor> visitor,
bool current_only) override;
CefRefPtr<CefNavigationEntry> GetVisibleNavigationEntry() override;
// CefBrowser methods:
CefRefPtr<CefBrowserHost> GetHost() override;
bool CanGoBack() override;
bool CanGoForward() override;
bool IsLoading() override;
int GetIdentifier() override;
bool IsSame(CefRefPtr<CefBrowser> that) override;
bool HasDocument() override;
bool IsPopup() override;
CefRefPtr<CefFrame> GetMainFrame() override;
CefRefPtr<CefFrame> GetFocusedFrame() override;
CefRefPtr<CefFrame> GetFrame(int64 identifier) override;
CefRefPtr<CefFrame> GetFrame(const CefString& name) override;
size_t GetFrameCount() override;
void GetFrameIdentifiers(std::vector<int64>& identifiers) override;
void GetFrameNames(std::vector<CefString>& names) override;
// CefBrowserContentsDelegate::Observer methods:
void OnStateChanged(CefBrowserContentsState state_changed) override;
void OnWebContentsDestroyed() override;
// Returns the frame associated with the specified RenderFrameHost.
CefRefPtr<CefFrame> GetFrameForHost(const content::RenderFrameHost* host);
// Returns the frame associated with the specified FrameTreeNode ID.
CefRefPtr<CefFrame> GetFrameForFrameTreeNode(int frame_tree_node_id);
// Manage observer objects. The observer must either outlive this object or
// be removed before destruction. Must be called on the UI thread.
void AddObserver(Observer* observer);
void RemoveObserver(Observer* observer);
bool HasObserver(Observer* observer) const;
// Methods called from CefFrameHostImpl.
void LoadMainFrameURL(const std::string& url,
const content::Referrer& referrer,
ui::PageTransition transition,
const std::string& extra_headers);
void OnDidFinishLoad(CefRefPtr<CefFrameHostImpl> frame,
const GURL& validated_url,
int http_status_code);
virtual void OnSetFocus(cef_focus_source_t source) = 0;
virtual void ViewText(const std::string& text) = 0;
// Helpers for executing client callbacks. Must be called on the UI thread.
void OnAfterCreated();
void OnBeforeClose();
void OnBrowserDestroyed();
// Thread-safe accessors.
const CefBrowserSettings& settings() const { return settings_; }
CefRefPtr<CefClient> client() const { return client_; }
scoped_refptr<CefBrowserInfo> browser_info() const { return browser_info_; }
int browser_id() const;
CefRefPtr<CefRequestContextImpl> request_context() const {
return request_context_;
}
// Accessors that must be called on the UI thread.
content::WebContents* GetWebContents() const;
content::BrowserContext* GetBrowserContext() const;
CefBrowserContentsDelegate* contents_delegate() const {
return contents_delegate_.get();
}
protected:
// Thread-safe members.
CefBrowserSettings settings_;
CefRefPtr<CefClient> client_;
scoped_refptr<CefBrowserInfo> browser_info_;
CefRefPtr<CefRequestContextImpl> request_context_;
// Only accessed on the UI thread.
std::unique_ptr<CefBrowserContentsDelegate> contents_delegate_;
// Observers that want to be notified of changes to this object.
// Only accessed on the UI thread.
base::ObserverList<Observer> observers_;
// Volatile state accessed from multiple threads. All access must be protected
// by |state_lock_|.
base::Lock state_lock_;
bool is_loading_ = false;
bool can_go_back_ = false;
bool can_go_forward_ = false;
bool has_document_ = false;
bool is_fullscreen_ = false;
CefRefPtr<CefFrameHostImpl> focused_frame_;
private:
IMPLEMENT_REFCOUNTING(CefBrowserHostBase);
DISALLOW_COPY_AND_ASSIGN(CefBrowserHostBase);
};
#endif // CEF_LIBCEF_BROWSER_BROWSER_HOST_BASE_H_

View File

@ -0,0 +1,144 @@
// Copyright (c) 2012 The Chromium Embedded Framework Authors.
// Portions copyright (c) 2011 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "include/cef_browser.h"
#include "libcef/browser/browser_host_impl.h"
#include "libcef/browser/chrome/chrome_browser_host_impl.h"
#include "libcef/browser/context.h"
#include "libcef/browser/thread_util.h"
#include "libcef/features/runtime.h"
namespace {
class CreateBrowserHelper {
public:
CreateBrowserHelper(const CefWindowInfo& windowInfo,
CefRefPtr<CefClient> client,
const CefString& url,
const CefBrowserSettings& settings,
CefRefPtr<CefDictionaryValue> extra_info,
CefRefPtr<CefRequestContext> request_context)
: window_info_(windowInfo),
client_(client),
url_(url),
settings_(settings),
extra_info_(extra_info),
request_context_(request_context) {}
CefWindowInfo window_info_;
CefRefPtr<CefClient> client_;
CefString url_;
CefBrowserSettings settings_;
CefRefPtr<CefDictionaryValue> extra_info_;
CefRefPtr<CefRequestContext> request_context_;
};
} // namespace
// static
bool CefBrowserHost::CreateBrowser(
const CefWindowInfo& windowInfo,
CefRefPtr<CefClient> client,
const CefString& url,
const CefBrowserSettings& settings,
CefRefPtr<CefDictionaryValue> extra_info,
CefRefPtr<CefRequestContext> request_context) {
// Verify that the context is in a valid state.
if (!CONTEXT_STATE_VALID()) {
NOTREACHED() << "context not valid";
return false;
}
// Verify that the settings structure is a valid size.
if (settings.size != sizeof(cef_browser_settings_t)) {
NOTREACHED() << "invalid CefBrowserSettings structure size";
return false;
}
// Verify windowless rendering requirements.
if (windowInfo.windowless_rendering_enabled &&
!client->GetRenderHandler().get()) {
NOTREACHED() << "CefRenderHandler implementation is required";
return false;
}
if (windowInfo.windowless_rendering_enabled &&
!CefContext::Get()->settings().windowless_rendering_enabled) {
LOG(ERROR) << "Creating a windowless browser without setting "
"CefSettings.windowless_rendering_enabled may result in "
"reduced performance or runtime errors.";
}
// Create the browser on the UI thread.
CreateBrowserHelper* helper = new CreateBrowserHelper(
windowInfo, client, url, settings, extra_info, request_context);
CEF_POST_TASK(CEF_UIT, base::BindOnce(
[](CreateBrowserHelper* helper) {
CefBrowserHost::CreateBrowserSync(
helper->window_info_, helper->client_,
helper->url_, helper->settings_,
helper->extra_info_,
helper->request_context_);
delete helper;
},
helper));
return true;
}
// static
CefRefPtr<CefBrowser> CefBrowserHost::CreateBrowserSync(
const CefWindowInfo& windowInfo,
CefRefPtr<CefClient> client,
const CefString& url,
const CefBrowserSettings& settings,
CefRefPtr<CefDictionaryValue> extra_info,
CefRefPtr<CefRequestContext> request_context) {
// Verify that the context is in a valid state.
if (!CONTEXT_STATE_VALID()) {
NOTREACHED() << "context not valid";
return nullptr;
}
// Verify that the settings structure is a valid size.
if (settings.size != sizeof(cef_browser_settings_t)) {
NOTREACHED() << "invalid CefBrowserSettings structure size";
return nullptr;
}
// Verify that this method is being called on the UI thread.
if (!CEF_CURRENTLY_ON_UIT()) {
NOTREACHED() << "called on invalid thread";
return nullptr;
}
// Verify windowless rendering requirements.
if (windowInfo.windowless_rendering_enabled &&
!client->GetRenderHandler().get()) {
NOTREACHED() << "CefRenderHandler implementation is required";
return nullptr;
}
CefBrowserHostBase::CreateParams create_params;
create_params.window_info.reset(new CefWindowInfo(windowInfo));
create_params.client = client;
create_params.url = GURL(url.ToString());
if (!url.empty() && !create_params.url.is_valid() &&
!create_params.url.has_scheme()) {
std::string new_url = std::string("http://") + url.ToString();
create_params.url = GURL(new_url);
}
create_params.settings = settings;
create_params.extra_info = extra_info;
create_params.request_context = request_context;
if (cef::IsChromeRuntimeEnabled()) {
auto browser = ChromeBrowserHostImpl::Create(create_params);
return browser.get();
}
auto browser = CefBrowserHostImpl::Create(create_params);
return browser.get();
}

File diff suppressed because it is too large Load Diff

View File

@ -14,7 +14,7 @@
#include "include/cef_browser.h"
#include "include/cef_client.h"
#include "include/cef_frame.h"
#include "include/views/cef_browser_view.h"
#include "libcef/browser/browser_host_base.h"
#include "libcef/browser/browser_info.h"
#include "libcef/browser/file_dialog_manager.h"
#include "libcef/browser/frame_host_impl.h"
@ -22,7 +22,6 @@
#include "libcef/browser/menu_manager.h"
#include "libcef/browser/request_context_impl.h"
#include "base/observer_list.h"
#include "base/strings/string16.h"
#include "base/synchronization/lock.h"
#include "content/public/browser/notification_observer.h"
@ -58,7 +57,9 @@ class CefBrowserPlatformDelegate;
class CefDevToolsManager;
class SiteInstance;
// Implementation of CefBrowser.
// CefBrowser implementation for the alloy runtime. Method calls are delegated
// to the CefPlatformDelegate or the WebContents as appropriate. All methods are
// thread-safe unless otherwise indicated.
//
// WebContentsDelegate: Interface for handling WebContents delegations. There is
// a one-to-one relationship between CefBrowserHostImpl and WebContents
@ -73,8 +74,7 @@ class SiteInstance;
// WebContentsObserver::routing_id() when sending IPC messages.
//
// NotificationObserver: Interface for observing post-processed notifications.
class CefBrowserHostImpl : public CefBrowserHost,
public CefBrowser,
class CefBrowserHostImpl : public CefBrowserHostBase,
public content::WebContentsDelegate,
public content::WebContentsObserver,
public content::NotificationObserver {
@ -85,58 +85,9 @@ class CefBrowserHostImpl : public CefBrowserHost,
virtual void OnResponse(const std::string& response) = 0;
};
// Interface to implement for observers that wish to be informed of changes
// to the CefBrowserHostImpl. All methods will be called on the UI thread.
class Observer {
public:
// Called before |browser| is destroyed. Any references to |browser| should
// be cleared when this method is called.
virtual void OnBrowserDestroyed(CefBrowserHostImpl* browser) = 0;
protected:
virtual ~Observer() {}
};
~CefBrowserHostImpl() override;
struct CreateParams {
// Platform-specific window creation info. Will be nullptr when creating a
// views-hosted browser.
std::unique_ptr<CefWindowInfo> window_info;
#if defined(USE_AURA)
// The BrowserView that will own a views-hosted browser. Will be nullptr for
// popup browsers (the BrowserView will be created later in that case).
CefRefPtr<CefBrowserView> browser_view;
#endif
// Client implementation. May be nullptr.
CefRefPtr<CefClient> client;
// Initial URL to load. May be empty. If this is a valid extension URL then
// the browser will be created as an app view extension host.
GURL url;
// Browser settings.
CefBrowserSettings settings;
// Other browser that opened this DevTools browser. Will be nullptr for non-
// DevTools browsers.
CefRefPtr<CefBrowserHostImpl> devtools_opener;
// Request context to use when creating the browser. If nullptr the global
// request context will be used.
CefRefPtr<CefRequestContext> request_context;
CefRefPtr<CefDictionaryValue> extra_info;
// Used when explicitly creating the browser as an extension host via
// ProcessManager::CreateBackgroundHost.
const extensions::Extension* extension = nullptr;
extensions::ViewType extension_host_type = extensions::VIEW_TYPE_INVALID;
};
// Create a new CefBrowserHostImpl instance.
// Create a new CefBrowserHostImpl instance with owned WebContents.
static CefRefPtr<CefBrowserHostImpl> Create(CreateParams& create_params);
// Returns the browser associated with the specified RenderViewHost.
@ -157,15 +108,12 @@ class CefBrowserHostImpl : public CefBrowserHost,
int render_routing_id);
// CefBrowserHost methods.
CefRefPtr<CefBrowser> GetBrowser() override;
void CloseBrowser(bool force_close) override;
bool TryCloseBrowser() override;
void SetFocus(bool focus) override;
CefWindowHandle GetWindowHandle() override;
CefWindowHandle GetOpenerWindowHandle() override;
bool HasView() override;
CefRefPtr<CefClient> GetClient() override;
CefRefPtr<CefRequestContext> GetRequestContext() override;
double GetZoomLevel() override;
void SetZoomLevel(double zoomLevel) override;
void RunFileDialog(FileDialogMode mode,
@ -174,12 +122,6 @@ class CefBrowserHostImpl : public CefBrowserHost,
const std::vector<CefString>& accept_filters,
int selected_accept_filter,
CefRefPtr<CefRunFileDialogCallback> callback) override;
void StartDownload(const CefString& url) override;
void DownloadImage(const CefString& image_url,
bool is_favicon,
uint32 max_image_size,
bool bypass_cache,
CefRefPtr<CefDownloadImageCallback> callback) override;
void Print() override;
void PrintToPDF(const CefString& path,
const CefPdfPrintSettings& settings,
@ -202,13 +144,9 @@ class CefBrowserHostImpl : public CefBrowserHost,
CefRefPtr<CefDictionaryValue> params) override;
CefRefPtr<CefRegistration> AddDevToolsMessageObserver(
CefRefPtr<CefDevToolsMessageObserver> observer) override;
void GetNavigationEntries(CefRefPtr<CefNavigationEntryVisitor> visitor,
bool current_only) override;
void SetMouseCursorChangeDisabled(bool disabled) override;
bool IsMouseCursorChangeDisabled() override;
bool IsWindowRenderingDisabled() override;
void ReplaceMisspelling(const CefString& word) override;
void AddWordToDictionary(const CefString& word) override;
void WasResized() override;
void WasHidden(bool hidden) override;
void NotifyScreenInfoChanged() override;
@ -249,7 +187,6 @@ class CefBrowserHostImpl : public CefBrowserHost,
void DragSourceEndedAt(int x, int y, DragOperationsMask op) override;
void SetAudioMuted(bool mute) override;
bool IsAudioMuted() override;
CefRefPtr<CefNavigationEntry> GetVisibleNavigationEntry() override;
void SetAccessibilityState(cef_state_t accessibility_state) override;
void SetAutoResizeEnabled(bool enabled,
const CefSize& min_size,
@ -258,26 +195,11 @@ class CefBrowserHostImpl : public CefBrowserHost,
bool IsBackgroundHost() override;
// CefBrowser methods.
CefRefPtr<CefBrowserHost> GetHost() override;
bool CanGoBack() override;
void GoBack() override;
bool CanGoForward() override;
void GoForward() override;
bool IsLoading() override;
void Reload() override;
void ReloadIgnoreCache() override;
void StopLoad() override;
int GetIdentifier() override;
bool IsSame(CefRefPtr<CefBrowser> that) override;
bool IsPopup() override;
bool HasDocument() override;
CefRefPtr<CefFrame> GetMainFrame() override;
CefRefPtr<CefFrame> GetFocusedFrame() override;
CefRefPtr<CefFrame> GetFrame(int64 identifier) override;
CefRefPtr<CefFrame> GetFrame(const CefString& name) override;
size_t GetFrameCount() override;
void GetFrameIdentifiers(std::vector<int64>& identifiers) override;
void GetFrameNames(std::vector<CefString>& names) override;
// Returns true if windowless rendering is enabled.
bool IsWindowless() const;
@ -293,7 +215,7 @@ class CefBrowserHostImpl : public CefBrowserHost,
// Destroy the browser members. This method should only be called after the
// native browser window is not longer processing messages.
void DestroyBrowser();
void DestroyBrowser() override;
// Cancel display of the context menu, if any.
void CancelContextMenu();
@ -308,25 +230,8 @@ class CefBrowserHostImpl : public CefBrowserHost,
CefRefPtr<CefBrowserView> GetBrowserView() const;
#endif
// Returns the frame associated with the specified RenderFrameHost.
CefRefPtr<CefFrame> GetFrameForHost(const content::RenderFrameHost* host);
// Returns the frame associated with the specified FrameTreeNode ID.
CefRefPtr<CefFrame> GetFrameForFrameTreeNode(int frame_tree_node_id);
// Load the specified URL in the main frame.
void LoadMainFrameURL(const std::string& url,
const content::Referrer& referrer,
ui::PageTransition transition,
const std::string& extra_headers);
// Called from CefFrameHostImpl.
void OnDidFinishLoad(CefRefPtr<CefFrameHostImpl> frame,
const GURL& validated_url,
int http_status_code);
// Open the specified text in the default text editor.
void ViewText(const std::string& text);
void ViewText(const std::string& text) override;
// Convert from view coordinates to screen coordinates. Potential display
// scaling will be applied to the result.
@ -341,20 +246,12 @@ class CefBrowserHostImpl : public CefBrowserHost,
void UpdateDragCursor(blink::WebDragOperation operation);
// Thread safe accessors.
const CefBrowserSettings& settings() const { return settings_; }
SkColor GetBackgroundColor() const;
CefRefPtr<CefClient> client() const { return client_; }
scoped_refptr<CefBrowserInfo> browser_info() const { return browser_info_; }
int browser_id() const;
CefRefPtr<CefRequestContextImpl> request_context() const {
return request_context_;
}
// Accessors that must be called on the UI thread.
content::BrowserContext* GetBrowserContext() const;
extensions::ExtensionHost* GetExtensionHost() const;
void OnSetFocus(cef_focus_source_t source);
void OnSetFocus(cef_focus_source_t source) override;
// Run the file chooser dialog specified by |params|. Only a single dialog may
// be pending at any given time. |callback| will be executed asynchronously
@ -387,7 +284,6 @@ class CefBrowserHostImpl : public CefBrowserHost,
bool* was_blocked) override;
void LoadingStateChanged(content::WebContents* source,
bool to_different_document) override;
void LoadProgressChanged(double progress) override;
void CloseContents(content::WebContents* source) override;
void UpdateTargetURL(content::WebContents* source, const GURL& url) override;
bool DidAddMessageToConsole(content::WebContents* source,
@ -467,61 +363,19 @@ class CefBrowserHostImpl : public CefBrowserHost,
// content::WebContentsObserver methods.
using content::WebContentsObserver::BeforeUnloadFired;
void RenderFrameCreated(content::RenderFrameHost* render_frame_host) override;
void RenderFrameHostChanged(content::RenderFrameHost* old_host,
content::RenderFrameHost* new_host) override;
void RenderFrameDeleted(content::RenderFrameHost* render_frame_host) override;
void RenderViewCreated(content::RenderViewHost* render_view_host) override;
void RenderViewDeleted(content::RenderViewHost* render_view_host) override;
void RenderViewReady() override;
void RenderProcessGone(base::TerminationStatus status) override;
void DidFinishNavigation(
content::NavigationHandle* navigation_handle) override;
void DidStopLoading() override;
void DocumentAvailableInMainFrame() override;
void DidFailLoad(content::RenderFrameHost* render_frame_host,
const GURL& validated_url,
int error_code) override;
void TitleWasSet(content::NavigationEntry* entry) override;
void PluginCrashed(const base::FilePath& plugin_path,
base::ProcessId plugin_pid) override;
void DidUpdateFaviconURL(
content::RenderFrameHost* render_frame_host,
const std::vector<blink::mojom::FaviconURLPtr>& candidates) override;
void OnAudioStateChanged(bool audible) override;
bool OnMessageReceived(const IPC::Message& message,
content::RenderFrameHost* render_frame_host) override;
void OnFrameFocused(content::RenderFrameHost* render_frame_host) override;
void AccessibilityEventReceived(
const content::AXEventNotificationDetails& content_event_bundle) override;
void AccessibilityLocationChangesReceived(
const std::vector<content::AXLocationChangeNotificationDetails>& locData)
override;
void OnWebContentsFocused(
content::RenderWidgetHost* render_widget_host) override;
void WebContentsDestroyed() override;
// Manage observer objects. The observer must either outlive this object or
// remove itself before destruction. These methods can only be called on the
// UI thread.
void AddObserver(Observer* observer);
void RemoveObserver(Observer* observer);
bool HasObserver(Observer* observer) const;
class NavigationLock final {
private:
friend class CefBrowserHostImpl;
friend std::unique_ptr<NavigationLock>::deleter_type;
explicit NavigationLock(CefRefPtr<CefBrowserHostImpl> browser);
~NavigationLock();
CefRefPtr<CefBrowserHostImpl> browser_;
};
// Block navigation-related events on NavigationLock life span.
std::unique_ptr<NavigationLock> CreateNavigationLock();
private:
friend class CefBrowserPlatformDelegateAlloy;
@ -555,21 +409,6 @@ class CefBrowserHostImpl : public CefBrowserHost,
// Give the platform delegate an opportunity to create the host window.
bool CreateHostWindow();
// Returns true if navigation actions are currently locked.
bool navigation_locked() const;
// Action to be executed once the navigation lock is released.
void set_pending_navigation_action(base::OnceClosure action);
void OnAddressChange(const GURL& url);
void OnLoadStart(CefRefPtr<CefFrame> frame,
ui::PageTransition transition_type);
void OnLoadError(CefRefPtr<CefFrame> frame, const GURL& url, int error_code);
void OnLoadEnd(CefRefPtr<CefFrame> frame,
const GURL& url,
int http_status_code);
void OnFullscreenModeChange(bool fullscreen);
void OnTitleChange(const base::string16& title);
// Create the CefFileDialogManager if it doesn't already exist.
void EnsureFileDialogManager();
@ -580,11 +419,7 @@ class CefBrowserHostImpl : public CefBrowserHost,
void InitializeDevToolsRegistrationOnUIThread(
CefRefPtr<CefRegistration> registration);
CefBrowserSettings settings_;
CefRefPtr<CefClient> client_;
scoped_refptr<CefBrowserInfo> browser_info_;
CefWindowHandle opener_;
CefRefPtr<CefRequestContextImpl> request_context_;
std::unique_ptr<CefBrowserPlatformDelegate> platform_delegate_;
const bool is_windowless_;
const bool is_views_hosted_;
@ -592,27 +427,10 @@ class CefBrowserHostImpl : public CefBrowserHost,
CefRefPtr<CefExtension> extension_;
bool is_background_host_ = false;
// Volatile state information. All access must be protected by the state lock.
base::Lock state_lock_;
bool is_loading_ = false;
bool can_go_back_ = false;
bool can_go_forward_ = false;
bool has_document_ = false;
bool is_fullscreen_ = false;
// The currently focused frame, or nullptr if the main frame is focused.
CefRefPtr<CefFrameHostImpl> focused_frame_;
// Represents the current browser destruction state. Only accessed on the UI
// thread.
DestructionState destruction_state_ = DESTRUCTION_STATE_NONE;
// Navigation will not occur while |navigation_lock_count_| > 0.
// |pending_navigation_action_| will be executed when the lock is released.
// Only accessed on the UI thread.
int navigation_lock_count_ = 0;
base::OnceClosure pending_navigation_action_;
// True if the OS window hosting the browser has been destroyed. Only accessed
// on the UI thread.
bool window_destroyed_ = false;
@ -643,9 +461,6 @@ class CefBrowserHostImpl : public CefBrowserHost,
// Used for creating and managing DevTools instances.
std::unique_ptr<CefDevToolsManager> devtools_manager_;
// Observers that want to be notified of changes to this object.
base::ObserverList<Observer>::Unchecked observers_;
// Used for capturing audio for CefAudioHandler.
std::unique_ptr<CefAudioCapturer> audio_capturer_;
@ -653,9 +468,6 @@ class CefBrowserHostImpl : public CefBrowserHost,
// starts running when a tab stops being audible, and is canceled if it starts
// being audible again before it fires.
base::OneShotTimer recently_audible_timer_;
IMPLEMENT_REFCOUNTING(CefBrowserHostImpl);
DISALLOW_COPY_AND_ASSIGN(CefBrowserHostImpl);
};
#endif // CEF_LIBCEF_BROWSER_BROWSER_HOST_IMPL_H_

View File

@ -34,12 +34,12 @@ CefBrowserInfo::CefBrowserInfo(int browser_id,
CefBrowserInfo::~CefBrowserInfo() {}
CefRefPtr<CefBrowserHostImpl> CefBrowserInfo::browser() const {
CefRefPtr<CefBrowserHostBase> CefBrowserInfo::browser() const {
base::AutoLock lock_scope(lock_);
return browser_;
}
void CefBrowserInfo::SetBrowser(CefRefPtr<CefBrowserHostImpl> browser) {
void CefBrowserInfo::SetBrowser(CefRefPtr<CefBrowserHostBase> browser) {
base::AutoLock lock_scope(lock_);
browser_ = browser;
@ -297,6 +297,37 @@ CefBrowserInfo::FrameHostList CefBrowserInfo::GetAllFrames() const {
return frames;
}
CefBrowserInfo::NavigationLock::NavigationLock() : weak_ptr_factory_(this) {}
CefBrowserInfo::NavigationLock::~NavigationLock() {
CEF_REQUIRE_UIT();
if (pending_action_) {
CEF_POST_TASK(CEF_UIT, std::move(pending_action_));
}
}
scoped_refptr<CefBrowserInfo::NavigationLock>
CefBrowserInfo::CreateNavigationLock() {
CEF_REQUIRE_UIT();
scoped_refptr<NavigationLock> lock;
if (!navigation_lock_) {
lock = new NavigationLock();
navigation_lock_ = lock->weak_ptr_factory_.GetWeakPtr();
} else {
lock = navigation_lock_.get();
}
return lock;
}
bool CefBrowserInfo::IsNavigationLocked(base::OnceClosure pending_action) {
CEF_REQUIRE_UIT();
if (navigation_lock_) {
navigation_lock_->pending_action_ = std::move(pending_action);
return true;
}
return false;
}
void CefBrowserInfo::MaybeUpdateFrameTreeNodeIdMap(FrameInfo* info) {
lock_.AssertAcquired();

View File

@ -12,8 +12,10 @@
#include "include/internal/cef_ptr.h"
#include "libcef/common/values_impl.h"
#include "base/callback.h"
#include "base/containers/unique_ptr_adapters.h"
#include "base/memory/ref_counted.h"
#include "base/memory/weak_ptr.h"
#include "base/synchronization/lock.h"
#include "base/values.h"
@ -21,12 +23,12 @@ namespace content {
class RenderFrameHost;
}
class CefBrowserHostImpl;
class CefBrowserHostBase;
class CefFrameHostImpl;
// CefBrowserInfo is used to associate a browser ID and render view/process
// IDs with a particular CefBrowserHostImpl. Render view/process IDs may change
// during the lifetime of a single CefBrowserHostImpl.
// IDs with a particular CefBrowserHostBase. Render view/process IDs may change
// during the lifetime of a single CefBrowserHostBase.
//
// CefBrowserInfo objects are managed by CefBrowserInfoManager and should not be
// created directly.
@ -44,23 +46,24 @@ class CefBrowserInfo : public base::RefCountedThreadSafe<CefBrowserInfo> {
// May return NULL if the browser has not yet been created or if the browser
// has been destroyed.
CefRefPtr<CefBrowserHostImpl> browser() const;
CefRefPtr<CefBrowserHostBase> browser() const;
// Set or clear the browser. Called from the CefBrowserHostImpl constructor
// Set or clear the browser. Called from CefBrowserHostBase InitializeBrowser
// (to set) and DestroyBrowser (to clear).
void SetBrowser(CefRefPtr<CefBrowserHostImpl> browser);
void SetBrowser(CefRefPtr<CefBrowserHostBase> browser);
// Ensure that a frame record exists for |host|. Called for the main frame
// when the RenderView is created, or for a sub-frame when the associated
// RenderFrame is created in the renderer process.
// Called from CefBrowserHostImpl::RenderFrameCreated (is_guest_view = false)
// or CefMimeHandlerViewGuestDelegate::OnGuestAttached (is_guest_view = true).
// Called from CefBrowserContentsDelegate::RenderFrameCreated (is_guest_view =
// false) or CefMimeHandlerViewGuestDelegate::OnGuestAttached (is_guest_view =
// true).
void MaybeCreateFrame(content::RenderFrameHost* host, bool is_guest_view);
// Remove the frame record for |host|. Called for the main frame when the
// RenderView is destroyed, or for a sub-frame when the associated RenderFrame
// is destroyed in the renderer process.
// Called from CefBrowserHostImpl::FrameDeleted or
// Called from CefBrowserContentsDelegate::RenderFrameDeleted or
// CefMimeHandlerViewGuestDelegate::OnGuestDetached.
void RemoveFrame(content::RenderFrameHost* host);
@ -121,6 +124,28 @@ class CefBrowserInfo : public base::RefCountedThreadSafe<CefBrowserInfo> {
typedef std::set<CefRefPtr<CefFrameHostImpl>> FrameHostList;
FrameHostList GetAllFrames() const;
class NavigationLock final : public base::RefCounted<NavigationLock> {
private:
friend class CefBrowserInfo;
friend class base::RefCounted<NavigationLock>;
NavigationLock();
~NavigationLock();
base::OnceClosure pending_action_;
base::WeakPtrFactory<NavigationLock> weak_ptr_factory_;
};
// Block navigation actions on NavigationLock life span. Must be called on the
// UI thread.
scoped_refptr<NavigationLock> CreateNavigationLock();
// Returns true if navigation actions are currently blocked. If this method
// returns true the most recent |pending_action| will be executed on the UI
// thread once the navigation lock is released. Must be called on the UI
// thread.
bool IsNavigationLocked(base::OnceClosure pending_action);
private:
friend class base::RefCountedThreadSafe<CefBrowserInfo>;
@ -151,11 +176,15 @@ class CefBrowserInfo : public base::RefCountedThreadSafe<CefBrowserInfo> {
bool is_windowless_;
CefRefPtr<CefDictionaryValue> extra_info_;
// Navigation will be blocked while |navigation_lock_| exists.
// Only accessed on the UI thread.
base::WeakPtr<NavigationLock> navigation_lock_;
mutable base::Lock lock_;
// The below members must be protected by |lock_|.
CefRefPtr<CefBrowserHostImpl> browser_;
CefRefPtr<CefBrowserHostBase> browser_;
// Owner of FrameInfo structs.
typedef std::set<std::unique_ptr<FrameInfo>, base::UniquePtrComparator>

View File

@ -14,6 +14,7 @@
#include "libcef/common/cef_switches.h"
#include "libcef/common/extensions/extensions_util.h"
#include "libcef/common/values_impl.h"
#include "libcef/features/runtime_checks.h"
#include "base/command_line.h"
#include "base/logging.h"
@ -116,6 +117,7 @@ bool CefBrowserInfoManager::CanCreateWindow(
bool opener_suppressed,
bool* no_javascript_access) {
CEF_REQUIRE_UIT();
REQUIRE_ALLOY_RUNTIME();
content::OpenURLParams params(target_url, referrer, disposition,
ui::PAGE_TRANSITION_LINK,
@ -180,7 +182,7 @@ bool CefBrowserInfoManager::CanCreateWindow(
}
if (allow) {
CefBrowserHostImpl::CreateParams create_params;
CefBrowserHostBase::CreateParams create_params;
if (!browser->IsViewsHosted())
create_params.window_info = std::move(window_info);
@ -213,6 +215,7 @@ void CefBrowserInfoManager::GetCustomWebContentsView(
content::WebContentsView** view,
content::RenderViewHostDelegateView** delegate_view) {
CEF_REQUIRE_UIT();
REQUIRE_ALLOY_RUNTIME();
std::unique_ptr<CefBrowserInfoManager::PendingPopup> pending_popup =
PopPendingPopup(CefBrowserInfoManager::PendingPopup::CAN_CREATE_WINDOW,
@ -240,6 +243,7 @@ void CefBrowserInfoManager::WebContentsCreated(
std::unique_ptr<CefBrowserPlatformDelegate>& platform_delegate,
CefRefPtr<CefDictionaryValue>& extra_info) {
CEF_REQUIRE_UIT();
REQUIRE_ALLOY_RUNTIME();
std::unique_ptr<CefBrowserInfoManager::PendingPopup> pending_popup =
PopPendingPopup(
@ -332,7 +336,7 @@ void CefBrowserInfoManager::DestroyAllBrowsers() {
if (!list.empty()) {
BrowserInfoList::iterator it = list.begin();
for (; it != list.end(); ++it) {
CefRefPtr<CefBrowserHostImpl> browser = (*it)->browser();
CefRefPtr<CefBrowserHostBase> browser = (*it)->browser();
DCHECK(browser.get());
if (browser.get()) {
// DestroyBrowser will call RemoveBrowserInfo.
@ -363,10 +367,11 @@ bool CefBrowserInfoManager::MaybeAllowNavigation(
const content::OpenURLParams& params,
CefRefPtr<CefBrowserHostImpl>& browser_out) const {
CEF_REQUIRE_UIT();
REQUIRE_ALLOY_RUNTIME();
bool is_guest_view = false;
CefRefPtr<CefBrowserHostImpl> browser =
extensions::GetOwnerBrowserForHost(opener, &is_guest_view);
CefRefPtr<CefBrowserHostImpl> browser = static_cast<CefBrowserHostImpl*>(
extensions::GetOwnerBrowserForHost(opener, &is_guest_view).get());
if (!browser) {
// Print preview uses a modal dialog where we don't own the WebContents.
// Allow that navigation to proceed.

View File

@ -37,6 +37,8 @@ namespace IPC {
class Message;
}
class CefBrowserHostBase;
class CefBrowserHostImpl;
class CefBrowserPlatformDelegate;
// Singleton object for managing BrowserInfo instances.
@ -48,7 +50,8 @@ class CefBrowserInfoManager : public content::RenderProcessHostObserver {
// Returns this singleton instance of this class.
static CefBrowserInfoManager* GetInstance();
// Called from CefBrowserHostImpl::Create when a new browser is being created
// Called from CefBrowserHostImpl::Create or
// ChromeBrowserDelegate::SetAsDelegate when a new browser is being created
// directly. In this case |is_popup| will be true only for DevTools browsers.
scoped_refptr<CefBrowserInfo> CreateBrowserInfo(
bool is_popup,
@ -107,7 +110,7 @@ class CefBrowserInfoManager : public content::RenderProcessHostObserver {
int render_routing_id,
IPC::Message* reply_msg);
// Called from CefBrowserHostImpl::DestroyBrowser() when a browser is
// Called from CefBrowserHostBase::DestroyBrowser() when a browser is
// destroyed.
void RemoveBrowserInfo(scoped_refptr<CefBrowserInfo> browser_info);
@ -116,7 +119,7 @@ class CefBrowserInfoManager : public content::RenderProcessHostObserver {
// Returns the CefBrowserInfo matching the specified IDs or nullptr if no
// match is found. It is allowed to add new callers of this method but
// consider using CefBrowserHostImpl::GetBrowserForFrameRoute() or
// consider using CefBrowserHostBase::GetBrowserForFrameRoute() or
// extensions::GetOwnerBrowserForFrameRoute() instead. If |is_guest_view| is
// non-nullptr it will be set to true if the IDs match a guest view associated
// with the returned browser info instead of the browser itself.
@ -127,7 +130,7 @@ class CefBrowserInfoManager : public content::RenderProcessHostObserver {
// Returns the CefBrowserInfo matching the specified ID or nullptr if no match
// is found. It is allowed to add new callers of this method but consider
// using CefBrowserHostImpl::GetBrowserForFrameTreeNode() instead. If
// using CefBrowserHostBase::GetBrowserForFrameTreeNode() instead. If
// |is_guest_view| is non-nullptr it will be set to true if the IDs match a
// guest view associated with the returned browser info instead of the browser
// itself.

View File

@ -54,13 +54,13 @@ class CefBrowserPlatformDelegate {
// Create a new CefBrowserPlatformDelegate instance. May be called on multiple
// threads.
static std::unique_ptr<CefBrowserPlatformDelegate> Create(
CefBrowserHostImpl::CreateParams& create_params);
CefBrowserHostBase::CreateParams& create_params);
// Called from CefBrowserHostImpl::Create.
// Wait for the call to WebContentsCreated(owned=true) before taking ownership
// of the resulting WebContents object.
virtual content::WebContents* CreateWebContents(
CefBrowserHostImpl::CreateParams& create_params,
CefBrowserHostBase::CreateParams& create_params,
bool& own_web_contents) = 0;
// Called to create the view objects for a new WebContents. Will only be

View File

@ -11,7 +11,6 @@
#include "base/memory/ptr_util.h"
#include "build/build_config.h"
#include "libcef/browser/chrome/browser_platform_delegate_chrome.h"
#include "libcef/browser/extensions/browser_platform_delegate_background.h"
#include "libcef/features/runtime_checks.h"
@ -69,7 +68,7 @@ std::unique_ptr<CefBrowserPlatformDelegateOsr> CreateOSRDelegate(
// static
std::unique_ptr<CefBrowserPlatformDelegate> CefBrowserPlatformDelegate::Create(
CefBrowserHostImpl::CreateParams& create_params) {
CefBrowserHostBase::CreateParams& create_params) {
const bool is_windowless =
create_params.window_info &&
create_params.window_info->windowless_rendering_enabled &&
@ -77,10 +76,6 @@ std::unique_ptr<CefBrowserPlatformDelegate> CefBrowserPlatformDelegate::Create(
const SkColor background_color = CefContext::Get()->GetBackgroundColor(
&create_params.settings, is_windowless ? STATE_ENABLED : STATE_DISABLED);
if (cef::IsChromeRuntimeEnabled()) {
return std::make_unique<CefBrowserPlatformDelegateChrome>(background_color);
}
if (create_params.window_info) {
std::unique_ptr<CefBrowserPlatformDelegateNative> native_delegate =
CreateNativeDelegate(*create_params.window_info.get(),

View File

@ -0,0 +1,45 @@
// Copyright 2020 The Chromium Embedded Framework Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CEF_LIBCEF_BROWSER_CHROME_BROWSER_DELEGATE_H_
#define CEF_LIBCEF_BROWSER_CHROME_BROWSER_DELEGATE_H_
#pragma once
#include <memory>
#include "base/memory/scoped_refptr.h"
#include "content/public/browser/web_contents_delegate.h"
class Browser;
namespace cef {
// Delegate for the chrome Browser object. Lifespan is controlled by the Browser
// object. See the ChromeBrowserDelegate documentation for additional details.
// Only accessed on the UI thread.
class BrowserDelegate : public content::WebContentsDelegate {
public:
// Opaque ref-counted base class for CEF-specific parameters passed via
// Browser::CreateParams::cef_params and possibly shared by multiple Browser
// instances.
class CreateParams : public base::RefCounted<CreateParams> {
public:
virtual ~CreateParams() {}
};
// Called from the Browser constructor to create a new delegate.
static std::unique_ptr<BrowserDelegate> Create(
Browser* browser,
scoped_refptr<CreateParams> cef_params);
~BrowserDelegate() override {}
// Add or remove ownership of the WebContents.
virtual void SetAsDelegate(content::WebContents* web_contents,
bool set_delegate) = 0;
};
} // namespace cef
#endif // CEF_LIBCEF_BROWSER_CHROME_BROWSER_DELEGATE_H_

View File

@ -1,138 +0,0 @@
// Copyright 2020 The Chromium Embedded Framework Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "libcef/browser/chrome/browser_platform_delegate_chrome.h"
#include "base/logging.h"
#include "chrome/browser/ui/browser.h"
#include "chrome/browser/ui/browser_tabstrip.h"
#include "chrome/browser/ui/browser_window.h"
#include "chrome/browser/ui/tabs/tab_strip_model.h"
CefBrowserPlatformDelegateChrome::CefBrowserPlatformDelegateChrome(
SkColor background_color)
: background_color_(background_color) {}
content::WebContents* CefBrowserPlatformDelegateChrome::CreateWebContents(
CefBrowserHostImpl::CreateParams& create_params,
bool& own_web_contents) {
// Get or create the request context and profile.
CefRefPtr<CefRequestContextImpl> request_context_impl =
CefRequestContextImpl::GetOrCreateForRequestContext(
create_params.request_context);
CHECK(request_context_impl);
auto cef_browser_context = request_context_impl->GetBrowserContext();
CHECK(cef_browser_context);
auto profile = cef_browser_context->AsProfile();
if (!create_params.request_context) {
// Using the global request context.
create_params.request_context = request_context_impl.get();
}
// Create a Browser.
Browser::CreateParams params =
Browser::CreateParams(profile, /*user_gesture=*/false);
chrome_browser_ = new Browser(params);
chrome::AddTabAt(chrome_browser_, create_params.url, /*idx=*/-1,
/*foreground=*/true);
auto web_contents =
chrome_browser_->tab_strip_model()->GetActiveWebContents();
CHECK(web_contents);
own_web_contents = false;
return web_contents;
}
void CefBrowserPlatformDelegateChrome::WebContentsDestroyed(
content::WebContents* web_contents) {
CefBrowserPlatformDelegate::WebContentsDestroyed(web_contents);
// TODO(chrome-runtime): Find a better way to be notified of Browser
// destruction.
browser_->WindowDestroyed();
}
void CefBrowserPlatformDelegateChrome::BrowserDestroyed(
CefBrowserHostImpl* browser) {
CefBrowserPlatformDelegate::BrowserDestroyed(browser);
// Release the reference added in CreateHostWindow.
browser->Release();
}
bool CefBrowserPlatformDelegateChrome::CreateHostWindow() {
// Keep a reference to the CEF browser.
browser_->AddRef();
chrome_browser_->window()->Show();
return true;
}
void CefBrowserPlatformDelegateChrome::CloseHostWindow() {}
CefWindowHandle CefBrowserPlatformDelegateChrome::GetHostWindowHandle() const {
return kNullWindowHandle;
}
SkColor CefBrowserPlatformDelegateChrome::GetBackgroundColor() const {
return background_color_;
}
void CefBrowserPlatformDelegateChrome::WasResized() {}
void CefBrowserPlatformDelegateChrome::SendKeyEvent(const CefKeyEvent& event) {}
void CefBrowserPlatformDelegateChrome::SendMouseClickEvent(
const CefMouseEvent& event,
CefBrowserHost::MouseButtonType type,
bool mouseUp,
int clickCount) {}
void CefBrowserPlatformDelegateChrome::SendMouseMoveEvent(
const CefMouseEvent& event,
bool mouseLeave) {}
void CefBrowserPlatformDelegateChrome::SendMouseWheelEvent(
const CefMouseEvent& event,
int deltaX,
int deltaY) {}
void CefBrowserPlatformDelegateChrome::SendTouchEvent(
const CefTouchEvent& event) {}
void CefBrowserPlatformDelegateChrome::SendFocusEvent(bool setFocus) {}
gfx::Point CefBrowserPlatformDelegateChrome::GetScreenPoint(
const gfx::Point& view) const {
return view;
}
void CefBrowserPlatformDelegateChrome::ViewText(const std::string& text) {}
bool CefBrowserPlatformDelegateChrome::HandleKeyboardEvent(
const content::NativeWebKeyboardEvent& event) {
return false;
}
CefEventHandle CefBrowserPlatformDelegateChrome::GetEventHandle(
const content::NativeWebKeyboardEvent& event) const {
return kNullEventHandle;
}
std::unique_ptr<CefMenuRunner>
CefBrowserPlatformDelegateChrome::CreateMenuRunner() {
NOTIMPLEMENTED();
return nullptr;
}
bool CefBrowserPlatformDelegateChrome::IsWindowless() const {
return false;
}
bool CefBrowserPlatformDelegateChrome::IsViewsHosted() const {
return false;
}

View File

@ -1,55 +0,0 @@
// Copyright 2020 The Chromium Embedded Framework Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CEF_LIBCEF_BROWSER_CHROME_BROWSER_PLATFORM_DELEGATE_CHROME_H_
#define CEF_LIBCEF_BROWSER_CHROME_BROWSER_PLATFORM_DELEGATE_CHROME_H_
#include "libcef/browser/browser_platform_delegate.h"
class Browser;
// Implementation of Chrome-based browser functionality.
class CefBrowserPlatformDelegateChrome : public CefBrowserPlatformDelegate {
public:
explicit CefBrowserPlatformDelegateChrome(SkColor background_color);
// CefBrowserPlatformDelegate overrides.
content::WebContents* CreateWebContents(
CefBrowserHostImpl::CreateParams& create_params,
bool& own_web_contents) override;
void WebContentsDestroyed(content::WebContents* web_contents) override;
void BrowserDestroyed(CefBrowserHostImpl* browser) override;
bool CreateHostWindow() override;
void CloseHostWindow() override;
CefWindowHandle GetHostWindowHandle() const override;
SkColor GetBackgroundColor() const override;
void WasResized() override;
void SendKeyEvent(const CefKeyEvent& event) override;
void SendMouseClickEvent(const CefMouseEvent& event,
CefBrowserHost::MouseButtonType type,
bool mouseUp,
int clickCount) override;
void SendMouseMoveEvent(const CefMouseEvent& event, bool mouseLeave) override;
void SendMouseWheelEvent(const CefMouseEvent& event,
int deltaX,
int deltaY) override;
void SendTouchEvent(const CefTouchEvent& event) override;
void SendFocusEvent(bool setFocus) override;
gfx::Point GetScreenPoint(const gfx::Point& view) const override;
void ViewText(const std::string& text) override;
bool HandleKeyboardEvent(
const content::NativeWebKeyboardEvent& event) override;
CefEventHandle GetEventHandle(
const content::NativeWebKeyboardEvent& event) const override;
std::unique_ptr<CefMenuRunner> CreateMenuRunner() override;
bool IsWindowless() const override;
bool IsViewsHosted() const override;
private:
const SkColor background_color_;
Browser* chrome_browser_;
};
#endif // CEF_LIBCEF_BROWSER_CHROME_BROWSER_PLATFORM_DELEGATE_CHROME_H_

View File

@ -0,0 +1,158 @@
// Copyright 2020 The Chromium Embedded Framework Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include <memory>
#include "libcef/browser/chrome/chrome_browser_delegate.h"
#include "libcef/browser/browser_contents_delegate.h"
#include "libcef/browser/browser_host_base.h"
#include "libcef/browser/browser_info_manager.h"
#include "libcef/browser/chrome/chrome_browser_host_impl.h"
#include "libcef/browser/request_context_impl.h"
#include "libcef/common/app_manager.h"
#include "chrome/browser/profiles/profile.h"
#include "chrome/browser/ui/browser.h"
ChromeBrowserDelegate::ChromeBrowserDelegate(
Browser* browser,
const CefBrowserHostBase::CreateParams& create_params)
: browser_(browser), create_params_(create_params) {
DCHECK(browser_);
}
ChromeBrowserDelegate::~ChromeBrowserDelegate() = default;
void ChromeBrowserDelegate::SetAsDelegate(content::WebContents* web_contents,
bool set_delegate) {
DCHECK(web_contents);
auto browser_host =
ChromeBrowserHostImpl::GetBrowserForContents(web_contents);
// |set_delegate=false| only makes sense if we already have a browser host.
DCHECK(browser_host || set_delegate);
if (browser_host) {
// We already have a browser host, so just change the associated Browser.
browser_host->SetBrowser(set_delegate ? browser_ : nullptr);
return;
}
auto request_context_impl =
CefRequestContextImpl::GetOrCreateForRequestContext(
create_params_.request_context);
// Check if chrome and CEF are using the same browser context.
// TODO(chrome-runtime): Verify if/when this might occur.
auto chrome_browser_context =
CefBrowserContext::FromBrowserContext(browser_->create_params().profile);
if (chrome_browser_context != request_context_impl->GetBrowserContext()) {
LOG(WARNING) << "Creating a chrome browser with mismatched context";
}
CefRefPtr<CefClient> client = create_params_.client;
if (!client) {
if (auto app = CefAppManager::Get()->GetApplication()) {
if (auto bph = app->GetBrowserProcessHandler()) {
client = bph->GetDefaultClient();
}
}
}
if (!client) {
LOG(WARNING) << "Creating a chrome browser without a client";
}
auto browser_info = CefBrowserInfoManager::GetInstance()->CreateBrowserInfo(
/*is_popup=*/false, /*is_windowless=*/false, create_params_.extra_info);
browser_host = new ChromeBrowserHostImpl(create_params_.settings, client,
browser_info, request_context_impl);
browser_host->Attach(browser_, web_contents);
}
void ChromeBrowserDelegate::LoadingStateChanged(content::WebContents* source,
bool to_different_document) {
if (auto delegate = GetDelegateForWebContents(source)) {
delegate->LoadingStateChanged(source, to_different_document);
}
}
void ChromeBrowserDelegate::UpdateTargetURL(content::WebContents* source,
const GURL& url) {
if (auto delegate = GetDelegateForWebContents(source)) {
delegate->UpdateTargetURL(source, url);
}
}
bool ChromeBrowserDelegate::DidAddMessageToConsole(
content::WebContents* source,
blink::mojom::ConsoleMessageLevel log_level,
const base::string16& message,
int32_t line_no,
const base::string16& source_id) {
if (auto delegate = GetDelegateForWebContents(source)) {
return delegate->DidAddMessageToConsole(source, log_level, message, line_no,
source_id);
}
return false;
}
void ChromeBrowserDelegate::DidNavigateMainFramePostCommit(
content::WebContents* web_contents) {
if (auto delegate = GetDelegateForWebContents(web_contents)) {
delegate->DidNavigateMainFramePostCommit(web_contents);
}
}
void ChromeBrowserDelegate::EnterFullscreenModeForTab(
content::RenderFrameHost* requesting_frame,
const blink::mojom::FullscreenOptions& options) {
auto web_contents =
content::WebContents::FromRenderFrameHost(requesting_frame);
if (!web_contents)
return;
if (auto delegate = GetDelegateForWebContents(web_contents)) {
delegate->EnterFullscreenModeForTab(requesting_frame, options);
}
}
void ChromeBrowserDelegate::ExitFullscreenModeForTab(
content::WebContents* web_contents) {
if (auto delegate = GetDelegateForWebContents(web_contents)) {
delegate->ExitFullscreenModeForTab(web_contents);
}
}
CefBrowserContentsDelegate* ChromeBrowserDelegate::GetDelegateForWebContents(
content::WebContents* web_contents) {
auto browser_host =
ChromeBrowserHostImpl::GetBrowserForContents(web_contents);
if (browser_host)
return browser_host->contents_delegate();
return nullptr;
}
namespace cef {
// static
std::unique_ptr<BrowserDelegate> BrowserDelegate::Create(
Browser* browser,
scoped_refptr<CreateParams> cef_params) {
CefBrowserHostBase::CreateParams create_params;
// Parameters from ChromeBrowserHostImpl::Create, or nullptr if the Browser
// was created from somewhere else.
auto params = static_cast<ChromeBrowserHostImpl::DelegateCreateParams*>(
cef_params.get());
if (params) {
create_params = params->create_params_;
}
return std::make_unique<ChromeBrowserDelegate>(browser, create_params);
}
} // namespace cef

View File

@ -0,0 +1,80 @@
// Copyright 2020 The Chromium Embedded Framework Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CEF_LIBCEF_BROWSER_CHROME_CHROME_BROWSER_DELEGATE_H_
#define CEF_LIBCEF_BROWSER_CHROME_CHROME_BROWSER_DELEGATE_H_
#pragma once
#include <memory>
#include "libcef/browser/browser_host_base.h"
#include "libcef/browser/browser_info.h"
#include "libcef/browser/chrome/browser_delegate.h"
#include "base/optional.h"
class CefBrowserContentsDelegate;
class CefRequestContextImpl;
class ChromeBrowserHostImpl;
// Implementation of the cef::BrowserDelegate interface. Lifespan is controlled
// by the Browser object. Only accessed on the UI thread.
//
// The Browser object represents the top-level Chrome browser window. One or
// more tabs (WebContents) are then owned by the Browser object via
// TabStripModel. A new Browser object can be created programmatically using
// "new Browser" or Browser::Create, or as a result of user action such as
// dragging a tab out of an existing window. New or existing tabs can also be
// added to an already existing Browser object.
//
// The Browser object acts as the WebContentsDelegate for all attached tabs. CEF
// integration requires WebContentsDelegate callbacks and notification of tab
// attach/detach. To support this integration a cef::BrowserDelegate
// (ChromeBrowserDelegate) member is created in the Browser constructor and
// receives delegation for the Browser callbacks. ChromeBrowserDelegate creates
// a new ChromeBrowserHostImpl when a tab is added to a Browser for the first
// time, and that ChromeBrowserHostImpl continues to exist until the tab's
// WebContents is destroyed. The associated WebContents object does not change,
// but the Browser object will change when the tab is dragged between windows.
class ChromeBrowserDelegate : public cef::BrowserDelegate {
public:
ChromeBrowserDelegate(Browser* browser,
const CefBrowserHostBase::CreateParams& create_params);
~ChromeBrowserDelegate() override;
// cef::BrowserDelegate methods:
void SetAsDelegate(content::WebContents* web_contents,
bool set_delegate) override;
// WebContentsDelegate methods:
void LoadingStateChanged(content::WebContents* source,
bool to_different_document) override;
void UpdateTargetURL(content::WebContents* source, const GURL& url) override;
bool DidAddMessageToConsole(content::WebContents* source,
blink::mojom::ConsoleMessageLevel log_level,
const base::string16& message,
int32_t line_no,
const base::string16& source_id) override;
void DidNavigateMainFramePostCommit(
content::WebContents* web_contents) override;
void EnterFullscreenModeForTab(
content::RenderFrameHost* requesting_frame,
const blink::mojom::FullscreenOptions& options) override;
void ExitFullscreenModeForTab(content::WebContents* web_contents) override;
Browser* browser() const { return browser_; }
private:
CefBrowserContentsDelegate* GetDelegateForWebContents(
content::WebContents* web_contents);
Browser* const browser_;
// Used when creating a new browser host.
const CefBrowserHostBase::CreateParams create_params_;
DISALLOW_COPY_AND_ASSIGN(ChromeBrowserDelegate);
};
#endif // CEF_LIBCEF_BROWSER_CHROME_CHROME_BROWSER_DELEGATE_H_

View File

@ -0,0 +1,508 @@
// Copyright 2020 The Chromium Embedded Framework Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "libcef/browser/chrome/chrome_browser_host_impl.h"
#include "libcef/browser/thread_util.h"
#include "libcef/features/runtime_checks.h"
#include "base/logging.h"
#include "base/notreached.h"
#include "chrome/browser/ui/browser.h"
#include "chrome/browser/ui/browser_commands.h"
#include "chrome/browser/ui/browser_tabstrip.h"
#include "chrome/browser/ui/browser_window.h"
#include "chrome/browser/ui/tabs/tab_strip_model.h"
namespace {
const auto kDefaultWindowDisposition = WindowOpenDisposition::CURRENT_TAB;
} // namespace
// static
CefRefPtr<ChromeBrowserHostImpl> ChromeBrowserHostImpl::Create(
const CreateParams& params) {
// Get or create the request context and profile.
CefRefPtr<CefRequestContextImpl> request_context_impl =
CefRequestContextImpl::GetOrCreateForRequestContext(
params.request_context);
CHECK(request_context_impl);
auto cef_browser_context = request_context_impl->GetBrowserContext();
CHECK(cef_browser_context);
auto profile = cef_browser_context->AsProfile();
Browser::CreateParams chrome_params =
Browser::CreateParams(profile, /*user_gesture=*/false);
// Pass |params| to cef::BrowserDelegate::Create from the Browser constructor.
chrome_params.cef_params = base::MakeRefCounted<DelegateCreateParams>(params);
// Create the Browser. This will indirectly create the ChomeBrowserDelegate.
// The same params will be used to create a new Browser if the tab is dragged
// out of the existing Browser.
auto browser = new Browser(chrome_params);
// Add a new tab. This will indirectly create a new tab WebContents and
// call ChromeBrowserDelegate::SetAsDelegate to create the associated
// ChromeBrowserHostImpl.
chrome::AddTabAt(browser, params.url, /*idx=*/-1, /*foreground=*/true);
browser->window()->Show();
// The new tab WebContents.
auto web_contents = browser->tab_strip_model()->GetActiveWebContents();
DCHECK(web_contents);
// The associated ChromeBrowserHostImpl.
auto browser_host =
ChromeBrowserHostImpl::GetBrowserForContents(web_contents);
DCHECK(browser_host);
return browser_host;
}
// static
CefRefPtr<ChromeBrowserHostImpl> ChromeBrowserHostImpl::GetBrowserForHost(
const content::RenderViewHost* host) {
REQUIRE_CHROME_RUNTIME();
auto browser = CefBrowserHostBase::GetBrowserForHost(host);
return static_cast<ChromeBrowserHostImpl*>(browser.get());
}
// static
CefRefPtr<ChromeBrowserHostImpl> ChromeBrowserHostImpl::GetBrowserForHost(
const content::RenderFrameHost* host) {
REQUIRE_CHROME_RUNTIME();
auto browser = CefBrowserHostBase::GetBrowserForHost(host);
return static_cast<ChromeBrowserHostImpl*>(browser.get());
}
// static
CefRefPtr<ChromeBrowserHostImpl> ChromeBrowserHostImpl::GetBrowserForContents(
const content::WebContents* contents) {
REQUIRE_CHROME_RUNTIME();
auto browser = CefBrowserHostBase::GetBrowserForContents(contents);
return static_cast<ChromeBrowserHostImpl*>(browser.get());
}
// static
CefRefPtr<ChromeBrowserHostImpl>
ChromeBrowserHostImpl::GetBrowserForFrameTreeNode(int frame_tree_node_id) {
REQUIRE_CHROME_RUNTIME();
auto browser =
CefBrowserHostBase::GetBrowserForFrameTreeNode(frame_tree_node_id);
return static_cast<ChromeBrowserHostImpl*>(browser.get());
}
// static
CefRefPtr<ChromeBrowserHostImpl> ChromeBrowserHostImpl::GetBrowserForFrameRoute(
int render_process_id,
int render_routing_id) {
REQUIRE_CHROME_RUNTIME();
auto browser = CefBrowserHostBase::GetBrowserForFrameRoute(render_process_id,
render_routing_id);
return static_cast<ChromeBrowserHostImpl*>(browser.get());
}
ChromeBrowserHostImpl::~ChromeBrowserHostImpl() = default;
void ChromeBrowserHostImpl::OnWebContentsDestroyed() {
DestroyBrowser();
}
void ChromeBrowserHostImpl::OnSetFocus(cef_focus_source_t source) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::ViewText(const std::string& text) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::CloseBrowser(bool force_close) {
NOTIMPLEMENTED();
}
bool ChromeBrowserHostImpl::TryCloseBrowser() {
NOTIMPLEMENTED();
return false;
}
void ChromeBrowserHostImpl::SetFocus(bool focus) {
NOTIMPLEMENTED();
}
CefWindowHandle ChromeBrowserHostImpl::GetWindowHandle() {
NOTIMPLEMENTED();
return kNullWindowHandle;
}
CefWindowHandle ChromeBrowserHostImpl::GetOpenerWindowHandle() {
NOTIMPLEMENTED();
return kNullWindowHandle;
}
bool ChromeBrowserHostImpl::HasView() {
NOTIMPLEMENTED();
return false;
}
double ChromeBrowserHostImpl::GetZoomLevel() {
NOTIMPLEMENTED();
return 0.0;
}
void ChromeBrowserHostImpl::SetZoomLevel(double zoomLevel) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::RunFileDialog(
FileDialogMode mode,
const CefString& title,
const CefString& default_file_path,
const std::vector<CefString>& accept_filters,
int selected_accept_filter,
CefRefPtr<CefRunFileDialogCallback> callback) {
NOTIMPLEMENTED();
callback->OnFileDialogDismissed(0, {});
}
void ChromeBrowserHostImpl::Print() {
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(CEF_UIT, base::BindOnce(&ChromeBrowserHostImpl::Print, this));
return;
}
if (browser_) {
chrome::Print(browser_);
}
}
void ChromeBrowserHostImpl::PrintToPDF(
const CefString& path,
const CefPdfPrintSettings& settings,
CefRefPtr<CefPdfPrintCallback> callback) {
NOTIMPLEMENTED();
callback->OnPdfPrintFinished(CefString(), false);
}
void ChromeBrowserHostImpl::Find(int identifier,
const CefString& searchText,
bool forward,
bool matchCase,
bool findNext) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::StopFinding(bool clearSelection) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::ShowDevTools(const CefWindowInfo& windowInfo,
CefRefPtr<CefClient> client,
const CefBrowserSettings& settings,
const CefPoint& inspect_element_at) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::CloseDevTools() {
NOTIMPLEMENTED();
}
bool ChromeBrowserHostImpl::HasDevTools() {
NOTIMPLEMENTED();
return false;
}
bool ChromeBrowserHostImpl::SendDevToolsMessage(const void* message,
size_t message_size) {
NOTIMPLEMENTED();
return false;
}
int ChromeBrowserHostImpl::ExecuteDevToolsMethod(
int message_id,
const CefString& method,
CefRefPtr<CefDictionaryValue> params) {
NOTIMPLEMENTED();
return 0;
}
CefRefPtr<CefRegistration> ChromeBrowserHostImpl::AddDevToolsMessageObserver(
CefRefPtr<CefDevToolsMessageObserver> observer) {
NOTIMPLEMENTED();
return nullptr;
}
void ChromeBrowserHostImpl::SetMouseCursorChangeDisabled(bool disabled) {
NOTIMPLEMENTED();
}
bool ChromeBrowserHostImpl::IsMouseCursorChangeDisabled() {
NOTIMPLEMENTED();
return false;
}
bool ChromeBrowserHostImpl::IsWindowRenderingDisabled() {
return false;
}
void ChromeBrowserHostImpl::WasResized() {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::WasHidden(bool hidden) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::NotifyScreenInfoChanged() {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::Invalidate(PaintElementType type) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::SendExternalBeginFrame() {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::SendKeyEvent(const CefKeyEvent& event) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::SendMouseClickEvent(const CefMouseEvent& event,
MouseButtonType type,
bool mouseUp,
int clickCount) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::SendMouseMoveEvent(const CefMouseEvent& event,
bool mouseLeave) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::SendMouseWheelEvent(const CefMouseEvent& event,
int deltaX,
int deltaY) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::SendTouchEvent(const CefTouchEvent& event) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::SendFocusEvent(bool setFocus) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::SendCaptureLostEvent() {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::NotifyMoveOrResizeStarted() {
NOTIMPLEMENTED();
}
int ChromeBrowserHostImpl::GetWindowlessFrameRate() {
return 0;
}
void ChromeBrowserHostImpl::SetWindowlessFrameRate(int frame_rate) {}
void ChromeBrowserHostImpl::ImeSetComposition(
const CefString& text,
const std::vector<CefCompositionUnderline>& underlines,
const CefRange& replacement_range,
const CefRange& selection_range) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::ImeCommitText(const CefString& text,
const CefRange& replacement_range,
int relative_cursor_pos) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::ImeFinishComposingText(bool keep_selection) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::ImeCancelComposition() {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::DragTargetDragEnter(
CefRefPtr<CefDragData> drag_data,
const CefMouseEvent& event,
DragOperationsMask allowed_ops) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::DragTargetDragOver(const CefMouseEvent& event,
DragOperationsMask allowed_ops) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::DragTargetDragLeave() {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::DragTargetDrop(const CefMouseEvent& event) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::DragSourceSystemDragEnded() {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::DragSourceEndedAt(int x,
int y,
DragOperationsMask op) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::SetAudioMuted(bool mute) {
NOTIMPLEMENTED();
}
bool ChromeBrowserHostImpl::IsAudioMuted() {
NOTIMPLEMENTED();
return false;
}
void ChromeBrowserHostImpl::SetAccessibilityState(
cef_state_t accessibility_state) {
NOTIMPLEMENTED();
}
void ChromeBrowserHostImpl::SetAutoResizeEnabled(bool enabled,
const CefSize& min_size,
const CefSize& max_size) {
NOTIMPLEMENTED();
}
CefRefPtr<CefExtension> ChromeBrowserHostImpl::GetExtension() {
return nullptr;
}
bool ChromeBrowserHostImpl::IsBackgroundHost() {
return false;
}
void ChromeBrowserHostImpl::GoBack() {
auto callback = base::BindOnce(&ChromeBrowserHostImpl::GoBack, this);
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(CEF_UIT, std::move(callback));
}
if (browser_info_->IsNavigationLocked(std::move(callback))) {
return;
}
if (browser_ && chrome::CanGoBack(browser_)) {
chrome::GoBack(browser_, kDefaultWindowDisposition);
}
}
void ChromeBrowserHostImpl::GoForward() {
auto callback = base::BindOnce(&ChromeBrowserHostImpl::GoForward, this);
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(CEF_UIT, std::move(callback));
}
if (browser_info_->IsNavigationLocked(std::move(callback))) {
return;
}
if (browser_ && chrome::CanGoForward(browser_)) {
chrome::GoForward(browser_, kDefaultWindowDisposition);
}
}
void ChromeBrowserHostImpl::Reload() {
auto callback = base::BindOnce(&ChromeBrowserHostImpl::Reload, this);
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(CEF_UIT, std::move(callback));
}
if (browser_info_->IsNavigationLocked(std::move(callback))) {
return;
}
if (browser_) {
chrome::Reload(browser_, kDefaultWindowDisposition);
}
}
void ChromeBrowserHostImpl::ReloadIgnoreCache() {
auto callback =
base::BindOnce(&ChromeBrowserHostImpl::ReloadIgnoreCache, this);
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(CEF_UIT, std::move(callback));
}
if (browser_info_->IsNavigationLocked(std::move(callback))) {
return;
}
if (browser_) {
chrome::ReloadBypassingCache(browser_, kDefaultWindowDisposition);
}
}
void ChromeBrowserHostImpl::StopLoad() {
auto callback = base::BindOnce(&ChromeBrowserHostImpl::StopLoad, this);
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(CEF_UIT, std::move(callback));
}
if (browser_info_->IsNavigationLocked(std::move(callback))) {
return;
}
if (browser_) {
chrome::Stop(browser_);
}
}
ChromeBrowserHostImpl::ChromeBrowserHostImpl(
const CefBrowserSettings& settings,
CefRefPtr<CefClient> client,
scoped_refptr<CefBrowserInfo> browser_info,
CefRefPtr<CefRequestContextImpl> request_context)
: CefBrowserHostBase(settings, client, browser_info, request_context) {}
void ChromeBrowserHostImpl::Attach(Browser* browser,
content::WebContents* web_contents) {
DCHECK(browser);
DCHECK(web_contents);
SetBrowser(browser);
contents_delegate_->ObserveWebContents(web_contents);
InitializeBrowser();
}
void ChromeBrowserHostImpl::SetBrowser(Browser* browser) {
CEF_REQUIRE_UIT();
browser_ = browser;
}
void ChromeBrowserHostImpl::InitializeBrowser() {
CEF_REQUIRE_UIT();
DCHECK(browser_);
CefBrowserHostBase::InitializeBrowser();
OnAfterCreated();
}
void ChromeBrowserHostImpl::DestroyBrowser() {
CEF_REQUIRE_UIT();
browser_ = nullptr;
OnBeforeClose();
OnBrowserDestroyed();
CefBrowserHostBase::DestroyBrowser();
}

View File

@ -0,0 +1,179 @@
// Copyright 2020 The Chromium Embedded Framework Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CEF_LIBCEF_BROWSER_CHROME_CHROME_BROWSER_HOST_IMPL_H_
#define CEF_LIBCEF_BROWSER_CHROME_CHROME_BROWSER_HOST_IMPL_H_
#pragma once
#include "libcef/browser/browser_host_base.h"
#include "libcef/browser/chrome/browser_delegate.h"
class Browser;
class ChromeBrowserDelegate;
// CefBrowser implementation for the chrome runtime. Method calls are delegated
// to the chrome Browser object or the WebContents as appropriate. See the
// ChromeBrowserDelegate documentation for additional details. All methods are
// thread-safe unless otherwise indicated.
class ChromeBrowserHostImpl : public CefBrowserHostBase {
public:
// CEF-specific parameters passed via Browser::CreateParams::cef_params and
// possibly shared by multiple Browser instances.
class DelegateCreateParams : public cef::BrowserDelegate::CreateParams {
public:
DelegateCreateParams(const CefBrowserHostBase::CreateParams& create_params)
: create_params_(create_params) {}
CefBrowserHostBase::CreateParams create_params_;
};
// Create a new Browser with a single tab (WebContents) and associated
// ChromeBrowserHostImpl instance.
static CefRefPtr<ChromeBrowserHostImpl> Create(const CreateParams& params);
// Returns the browser associated with the specified RenderViewHost.
static CefRefPtr<ChromeBrowserHostImpl> GetBrowserForHost(
const content::RenderViewHost* host);
// Returns the browser associated with the specified RenderFrameHost.
static CefRefPtr<ChromeBrowserHostImpl> GetBrowserForHost(
const content::RenderFrameHost* host);
// Returns the browser associated with the specified WebContents.
static CefRefPtr<ChromeBrowserHostImpl> GetBrowserForContents(
const content::WebContents* contents);
// Returns the browser associated with the specified FrameTreeNode ID.
static CefRefPtr<ChromeBrowserHostImpl> GetBrowserForFrameTreeNode(
int frame_tree_node_id);
// Returns the browser associated with the specified frame routing IDs.
static CefRefPtr<ChromeBrowserHostImpl> GetBrowserForFrameRoute(
int render_process_id,
int render_routing_id);
~ChromeBrowserHostImpl() override;
// CefBrowserContentsDelegate::Observer methods:
void OnWebContentsDestroyed() override;
// CefBrowserHostBase methods called from CefFrameHostImpl:
void OnSetFocus(cef_focus_source_t source) override;
void ViewText(const std::string& text) override;
// CefBrowserHost methods:
void CloseBrowser(bool force_close) override;
bool TryCloseBrowser() override;
void SetFocus(bool focus) override;
CefWindowHandle GetWindowHandle() override;
CefWindowHandle GetOpenerWindowHandle() override;
bool HasView() override;
double GetZoomLevel() override;
void SetZoomLevel(double zoomLevel) override;
void RunFileDialog(FileDialogMode mode,
const CefString& title,
const CefString& default_file_path,
const std::vector<CefString>& accept_filters,
int selected_accept_filter,
CefRefPtr<CefRunFileDialogCallback> callback) override;
void Print() override;
void PrintToPDF(const CefString& path,
const CefPdfPrintSettings& settings,
CefRefPtr<CefPdfPrintCallback> callback) override;
void Find(int identifier,
const CefString& searchText,
bool forward,
bool matchCase,
bool findNext) override;
void StopFinding(bool clearSelection) override;
void ShowDevTools(const CefWindowInfo& windowInfo,
CefRefPtr<CefClient> client,
const CefBrowserSettings& settings,
const CefPoint& inspect_element_at) override;
void CloseDevTools() override;
bool HasDevTools() override;
bool SendDevToolsMessage(const void* message, size_t message_size) override;
int ExecuteDevToolsMethod(int message_id,
const CefString& method,
CefRefPtr<CefDictionaryValue> params) override;
CefRefPtr<CefRegistration> AddDevToolsMessageObserver(
CefRefPtr<CefDevToolsMessageObserver> observer) override;
void SetMouseCursorChangeDisabled(bool disabled) override;
bool IsMouseCursorChangeDisabled() override;
bool IsWindowRenderingDisabled() override;
void WasResized() override;
void WasHidden(bool hidden) override;
void NotifyScreenInfoChanged() override;
void Invalidate(PaintElementType type) override;
void SendExternalBeginFrame() override;
void SendKeyEvent(const CefKeyEvent& event) override;
void SendMouseClickEvent(const CefMouseEvent& event,
MouseButtonType type,
bool mouseUp,
int clickCount) override;
void SendMouseMoveEvent(const CefMouseEvent& event, bool mouseLeave) override;
void SendMouseWheelEvent(const CefMouseEvent& event,
int deltaX,
int deltaY) override;
void SendTouchEvent(const CefTouchEvent& event) override;
void SendFocusEvent(bool setFocus) override;
void SendCaptureLostEvent() override;
void NotifyMoveOrResizeStarted() override;
int GetWindowlessFrameRate() override;
void SetWindowlessFrameRate(int frame_rate) override;
void ImeSetComposition(const CefString& text,
const std::vector<CefCompositionUnderline>& underlines,
const CefRange& replacement_range,
const CefRange& selection_range) override;
void ImeCommitText(const CefString& text,
const CefRange& replacement_range,
int relative_cursor_pos) override;
void ImeFinishComposingText(bool keep_selection) override;
void ImeCancelComposition() override;
void DragTargetDragEnter(CefRefPtr<CefDragData> drag_data,
const CefMouseEvent& event,
DragOperationsMask allowed_ops) override;
void DragTargetDragOver(const CefMouseEvent& event,
DragOperationsMask allowed_ops) override;
void DragTargetDragLeave() override;
void DragTargetDrop(const CefMouseEvent& event) override;
void DragSourceSystemDragEnded() override;
void DragSourceEndedAt(int x, int y, DragOperationsMask op) override;
void SetAudioMuted(bool mute) override;
bool IsAudioMuted() override;
void SetAccessibilityState(cef_state_t accessibility_state) override;
void SetAutoResizeEnabled(bool enabled,
const CefSize& min_size,
const CefSize& max_size) override;
CefRefPtr<CefExtension> GetExtension() override;
bool IsBackgroundHost() override;
// CefBrowser methods:
void GoBack() override;
void GoForward() override;
void Reload() override;
void ReloadIgnoreCache() override;
void StopLoad() override;
private:
friend class ChromeBrowserDelegate;
ChromeBrowserHostImpl(const CefBrowserSettings& settings,
CefRefPtr<CefClient> client,
scoped_refptr<CefBrowserInfo> browser_info,
CefRefPtr<CefRequestContextImpl> request_context);
// Called from ChromeBrowserDelegate::SetAsDelegate when this object is first
// created. Must be called on the UI thread.
void Attach(Browser* browser, content::WebContents* web_contents);
// Called from ChromeBrowserDelegate::SetAsDelegate when this object changes
// Browser ownership (e.g. dragging between windows). The old Browser will be
// cleared before the new Browser is added. Must be called on the UI thread.
void SetBrowser(Browser* browser);
// CefBrowserHostBase methods:
void InitializeBrowser() override;
void DestroyBrowser() override;
Browser* browser_ = nullptr;
};
#endif // CEF_LIBCEF_BROWSER_CHROME_CHROME_BROWSER_HOST_IMPL_H_

View File

@ -249,7 +249,7 @@ CefDevToolsFrontend* CefDevToolsFrontend::Show(
new_settings.background_color = SK_ColorWHITE;
}
CefBrowserHostImpl::CreateParams create_params;
CefBrowserHostBase::CreateParams create_params;
if (!inspected_browser->IsViewsHosted())
create_params.window_info.reset(new CefWindowInfo(windowInfo));
create_params.client = client;

View File

@ -5,6 +5,7 @@
#include "libcef/browser/download_manager_delegate.h"
#include "include/cef_download_handler.h"
#include "libcef/browser/browser_host_impl.h"
#include "libcef/browser/context.h"
#include "libcef/browser/download_item_impl.h"
#include "libcef/browser/thread_util.h"
@ -405,7 +406,7 @@ std::string CefDownloadManagerDelegate::ApplicationClientIdForFileScanning() {
}
void CefDownloadManagerDelegate::OnBrowserDestroyed(
CefBrowserHostImpl* browser) {
CefBrowserHostBase* browser) {
ItemBrowserMap::iterator it = item_browser_map_.begin();
for (; it != item_browser_map_.end(); ++it) {
if (it->second == browser) {

View File

@ -8,7 +8,7 @@
#include <set>
#include "libcef/browser/browser_host_impl.h"
#include "libcef/browser/browser_host_base.h"
#include "base/compiler_specific.h"
#include "base/memory/weak_ptr.h"
@ -16,10 +16,12 @@
#include "content/public/browser/download_manager.h"
#include "content/public/browser/download_manager_delegate.h"
class CefBrowserHostImpl;
class CefDownloadManagerDelegate : public download::DownloadItem::Observer,
public content::DownloadManager::Observer,
public content::DownloadManagerDelegate,
public CefBrowserHostImpl::Observer {
public CefBrowserHostBase::Observer {
public:
explicit CefDownloadManagerDelegate(content::DownloadManager* manager);
~CefDownloadManagerDelegate() override;
@ -41,8 +43,8 @@ class CefDownloadManagerDelegate : public download::DownloadItem::Observer,
void GetNextId(content::DownloadIdCallback callback) override;
std::string ApplicationClientIdForFileScanning() override;
// CefBrowserHostImpl::Observer methods.
void OnBrowserDestroyed(CefBrowserHostImpl* browser) override;
// CefBrowserHostBase::Observer methods.
void OnBrowserDestroyed(CefBrowserHostBase* browser) override;
CefBrowserHostImpl* GetOrAssociateBrowser(download::DownloadItem* item);
CefBrowserHostImpl* GetBrowser(download::DownloadItem* item);

View File

@ -5,9 +5,12 @@
#include "libcef/browser/extensions/browser_extensions_util.h"
#include "libcef/browser/browser_context.h"
#include "libcef/browser/browser_host_base.h"
#include "libcef/browser/browser_host_impl.h"
#include "libcef/browser/browser_info_manager.h"
#include "libcef/browser/thread_util.h"
#include "libcef/common/extensions/extensions_util.h"
#include "libcef/features/runtime_checks.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/printing/print_preview_dialog_controller.h"
@ -16,6 +19,8 @@
#include "content/browser/web_contents/web_contents_impl.h"
#include "content/public/browser/browser_context.h"
#include "content/public/browser/browser_plugin_guest_manager.h"
#include "content/public/browser/render_frame_host.h"
#include "content/public/browser/render_view_host.h"
#include "extensions/browser/extension_registry.h"
namespace extensions {
@ -69,7 +74,7 @@ content::WebContents* GetOwnerForGuestContents(content::WebContents* guest) {
return print_preview_controller->GetInitiator(guest);
}
CefRefPtr<CefBrowserHostImpl> GetOwnerBrowserForFrameRoute(
CefRefPtr<CefBrowserHostBase> GetOwnerBrowserForFrameRoute(
int render_process_id,
int render_routing_id,
bool* is_guest_view) {
@ -86,7 +91,7 @@ CefRefPtr<CefBrowserHostImpl> GetOwnerBrowserForFrameRoute(
CefBrowserInfoManager::GetInstance()->GetBrowserInfoForFrameRoute(
render_process_id, render_routing_id, is_guest_view);
if (info.get()) {
CefRefPtr<CefBrowserHostImpl> browser = info->browser();
CefRefPtr<CefBrowserHostBase> browser = info->browser();
if (!browser.get()) {
LOG(WARNING) << "Found browser id " << info->browser_id()
<< " but no browser object matching view process id "
@ -99,20 +104,20 @@ CefRefPtr<CefBrowserHostImpl> GetOwnerBrowserForFrameRoute(
}
}
CefRefPtr<CefBrowserHostImpl> GetOwnerBrowserForHost(
CefRefPtr<CefBrowserHostBase> GetOwnerBrowserForHost(
content::RenderViewHost* host,
bool* is_guest_view) {
if (is_guest_view)
*is_guest_view = false;
CefRefPtr<CefBrowserHostImpl> browser =
CefBrowserHostImpl::GetBrowserForHost(host);
CefRefPtr<CefBrowserHostBase> browser =
CefBrowserHostBase::GetBrowserForHost(host);
if (!browser.get() && ExtensionsEnabled()) {
// Retrieve the owner browser, if any.
content::WebContents* owner = GetOwnerForGuestContents(
content::WebContents::FromRenderViewHost(host));
if (owner) {
browser = CefBrowserHostImpl::GetBrowserForContents(owner);
browser = CefBrowserHostBase::GetBrowserForContents(owner);
if (browser.get() && is_guest_view)
*is_guest_view = true;
}
@ -120,20 +125,20 @@ CefRefPtr<CefBrowserHostImpl> GetOwnerBrowserForHost(
return browser;
}
CefRefPtr<CefBrowserHostImpl> GetOwnerBrowserForHost(
CefRefPtr<CefBrowserHostBase> GetOwnerBrowserForHost(
content::RenderFrameHost* host,
bool* is_guest_view) {
if (is_guest_view)
*is_guest_view = false;
CefRefPtr<CefBrowserHostImpl> browser =
CefBrowserHostImpl::GetBrowserForHost(host);
CefRefPtr<CefBrowserHostBase> browser =
CefBrowserHostBase::GetBrowserForHost(host);
if (!browser.get() && ExtensionsEnabled()) {
// Retrieve the owner browser, if any.
content::WebContents* owner = GetOwnerForGuestContents(
content::WebContents::FromRenderFrameHost(host));
if (owner) {
browser = CefBrowserHostImpl::GetBrowserForContents(owner);
browser = CefBrowserHostBase::GetBrowserForContents(owner);
if (browser.get() && is_guest_view)
*is_guest_view = true;
}
@ -144,6 +149,7 @@ CefRefPtr<CefBrowserHostImpl> GetOwnerBrowserForHost(
CefRefPtr<CefBrowserHostImpl> GetBrowserForTabId(
int tab_id,
content::BrowserContext* browser_context) {
REQUIRE_ALLOY_RUNTIME();
CEF_REQUIRE_UIT();
DCHECK(browser_context);
if (tab_id < 0 || !browser_context)
@ -154,7 +160,8 @@ CefRefPtr<CefBrowserHostImpl> GetBrowserForTabId(
for (const auto& browser_info :
CefBrowserInfoManager::GetInstance()->GetBrowserInfoList()) {
CefRefPtr<CefBrowserHostImpl> current_browser = browser_info->browser();
CefRefPtr<CefBrowserHostImpl> current_browser =
static_cast<CefBrowserHostImpl*>(browser_info->browser().get());
if (current_browser && current_browser->GetIdentifier() == tab_id) {
// Make sure we're operating in the same CefBrowserContext.
if (CefBrowserContext::FromBrowserContext(

View File

@ -7,16 +7,20 @@
#include <vector>
#include "libcef/browser/browser_host_impl.h"
#include "include/internal/cef_ptr.h"
#include "url/gurl.h"
namespace content {
class BrowserContext;
class RenderFrameHost;
class RenderViewHost;
class WebContents;
} // namespace content
class CefBrowserHostBase;
class CefBrowserHostImpl;
namespace extensions {
class Extension;
@ -32,24 +36,24 @@ void GetAllGuestsForOwnerContents(content::WebContents* owner,
// Returns the WebContents that owns the specified |guest|, if any.
content::WebContents* GetOwnerForGuestContents(content::WebContents* guest);
// Returns the CefBrowserHostImpl that owns the host identified by the specified
// Returns the CefBrowserHostBase that owns the host identified by the specified
// routing IDs, if any. |is_guest_view| will be set to true if the IDs
// match a guest view associated with the returned browser instead of the
// browser itself.
CefRefPtr<CefBrowserHostImpl> GetOwnerBrowserForFrameRoute(
CefRefPtr<CefBrowserHostBase> GetOwnerBrowserForFrameRoute(
int render_process_id,
int render_routing_id,
bool* is_guest_view);
// Returns the CefBrowserHostImpl that owns the specified |host|, if any.
// Returns the CefBrowserHostBase that owns the specified |host|, if any.
// |is_guest_view| will be set to true if the host matches a guest view
// associated with the returned browser instead of the browser itself.
// TODO(cef): Delete the RVH variant once the remaining use case
// (via AlloyContentBrowserClient::OverrideWebkitPrefs) has been removed.
CefRefPtr<CefBrowserHostImpl> GetOwnerBrowserForHost(
CefRefPtr<CefBrowserHostBase> GetOwnerBrowserForHost(
content::RenderViewHost* host,
bool* is_guest_view);
CefRefPtr<CefBrowserHostImpl> GetOwnerBrowserForHost(
CefRefPtr<CefBrowserHostBase> GetOwnerBrowserForHost(
content::RenderFrameHost* host,
bool* is_guest_view);

View File

@ -365,7 +365,7 @@ base::DictionaryValue* CefExtensionFunctionDetails::OpenTab(
if (!request_context)
return nullptr;
CefBrowserHostImpl::CreateParams create_params;
CefBrowserHostBase::CreateParams create_params;
create_params.url = url;
create_params.request_context = request_context;
create_params.window_info.reset(new CefWindowInfo);

View File

@ -250,7 +250,7 @@ bool CefExtensionsBrowserClient::CreateBackgroundExtensionHost(
return true;
}
CefBrowserHostImpl::CreateParams create_params;
CefBrowserHostBase::CreateParams create_params;
create_params.url = url;
create_params.request_context = request_context;

View File

@ -8,7 +8,7 @@
#include "include/cef_stream.h"
#include "include/cef_v8.h"
#include "include/test/cef_test_helpers.h"
#include "libcef/browser/browser_host_impl.h"
#include "libcef/browser/browser_host_base.h"
#include "libcef/browser/navigate_params.h"
#include "libcef/browser/net_service/browser_urlrequest_impl.h"
#include "libcef/common/cef_messages.h"
@ -45,7 +45,7 @@ class ViewTextHandler : public CefResponseManager::Handler {
void OnResponse(const Cef_Response_Params& params) override {
CefRefPtr<CefBrowser> browser = frame_->GetBrowser();
if (browser.get()) {
static_cast<CefBrowserHostImpl*>(browser.get())
static_cast<CefBrowserHostBase*>(browser.get())
->ViewText(params.response);
}
}
@ -114,7 +114,7 @@ void CefFrameHostImpl::SetRenderFrameHost(content::RenderFrameHost* host) {
}
bool CefFrameHostImpl::IsValid() {
return !!GetBrowserHostImpl();
return !!GetBrowserHostBase();
}
void CefFrameHostImpl::Undo() {
@ -203,7 +203,7 @@ CefRefPtr<CefFrame> CefFrameHostImpl::GetParent() {
parent_frame_id = parent_frame_id_;
}
auto browser = GetBrowserHostImpl();
auto browser = GetBrowserHostBase();
if (browser)
return browser->GetFrame(parent_frame_id);
@ -216,7 +216,7 @@ CefString CefFrameHostImpl::GetURL() {
}
CefRefPtr<CefBrowser> CefFrameHostImpl::GetBrowser() {
return GetBrowserHostImpl().get();
return GetBrowserHostBase().get();
}
CefRefPtr<CefV8Context> CefFrameHostImpl::GetV8Context() {
@ -239,7 +239,7 @@ CefRefPtr<CefURLRequest> CefFrameHostImpl::CreateURLRequest(
return nullptr;
}
auto browser = GetBrowserHostImpl();
auto browser = GetBrowserHostBase();
if (!browser)
return nullptr;
@ -323,7 +323,7 @@ void CefFrameHostImpl::Navigate(const CefNavigateParams& params) {
Send(new CefMsg_LoadRequest(MSG_ROUTING_NONE, request));
auto browser = GetBrowserHostImpl();
auto browser = GetBrowserHostBase();
if (browser)
browser->OnSetFocus(FOCUS_SOURCE_NAVIGATION);
}
@ -339,7 +339,7 @@ void CefFrameHostImpl::LoadURLWithExtras(const std::string& url,
if (frame_id == CefFrameHostImpl::kMainFrameId) {
// Load via the browser using NavigationController.
auto browser = GetBrowserHostImpl();
auto browser = GetBrowserHostBase();
if (browser) {
browser->LoadMainFrameURL(url, referrer, transition, extra_headers);
}
@ -553,7 +553,7 @@ int64 CefFrameHostImpl::GetFrameId() const {
return is_main_frame_ ? kMainFrameId : frame_id_;
}
CefRefPtr<CefBrowserHostImpl> CefFrameHostImpl::GetBrowserHostImpl() const {
CefRefPtr<CefBrowserHostBase> CefFrameHostImpl::GetBrowserHostBase() const {
base::AutoLock lock_scope(state_lock_);
if (browser_info_)
return browser_info_->browser();
@ -572,14 +572,14 @@ void CefFrameHostImpl::OnAttached() {
void CefFrameHostImpl::OnDidFinishLoad(const GURL& validated_url,
int http_status_code) {
auto browser = GetBrowserHostImpl();
auto browser = GetBrowserHostBase();
if (browser)
browser->OnDidFinishLoad(this, validated_url, http_status_code);
}
void CefFrameHostImpl::OnUpdateDraggableRegions(
const std::vector<Cef_DraggableRegion_Params>& regions) {
auto browser = GetBrowserHostImpl();
auto browser = GetBrowserHostBase();
if (!browser)
return;
@ -611,12 +611,12 @@ void CefFrameHostImpl::OnRequest(const Cef_Request_Params& params) {
bool expect_response_ack = false;
if (params.user_initiated) {
auto browser = GetBrowserHostImpl();
if (browser && browser->client()) {
auto browser = GetBrowserHostBase();
if (browser && browser->GetClient()) {
// Give the user a chance to handle the request.
CefRefPtr<CefProcessMessageImpl> message(new CefProcessMessageImpl(
const_cast<Cef_Request_Params*>(&params), false, true));
success = browser->client()->OnProcessMessageReceived(
success = browser->GetClient()->OnProcessMessageReceived(
browser.get(), this, PID_RENDERER, message.get());
message->Detach(nullptr);
}

View File

@ -31,7 +31,7 @@ struct Cef_DraggableRegion_Params;
struct Cef_Request_Params;
struct Cef_Response_Params;
class CefBrowserInfo;
class CefBrowserHostImpl;
class CefBrowserHostBase;
struct CefNavigateParams;
// Implementation of CefFrame. CefFrameHostImpl objects should always be created
@ -112,10 +112,10 @@ class CefFrameHostImpl : public CefFrame {
const std::string& scriptUrl,
int startLine);
// Called from CefBrowserHostImpl::DidStopLoading.
// Called from CefBrowserHostBase::DidStopLoading.
void MaybeSendDidStopLoading();
// Called from CefBrowserHostImpl::OnMessageReceived.
// Called from CefBrowserHostBase::OnMessageReceived.
bool OnMessageReceived(const IPC::Message& message);
void ExecuteJavaScriptWithUserGestureForTests(const CefString& javascript);
@ -145,7 +145,7 @@ class CefFrameHostImpl : public CefFrame {
private:
int64 GetFrameId() const;
CefRefPtr<CefBrowserHostImpl> GetBrowserHostImpl() const;
CefRefPtr<CefBrowserHostBase> GetBrowserHostBase() const;
// OnMessageReceived message handlers.
void OnAttached();

View File

@ -4,7 +4,7 @@
#include "libcef/browser/net_service/resource_request_handler_wrapper.h"
#include "libcef/browser/browser_host_impl.h"
#include "libcef/browser/browser_host_base.h"
#include "libcef/browser/browser_platform_delegate.h"
#include "libcef/browser/context.h"
#include "libcef/browser/iothread_state.h"
@ -80,7 +80,7 @@ class RequestCallbackWrapper : public CefRequestCallback {
};
std::string GetAcceptLanguageList(content::BrowserContext* browser_context,
CefRefPtr<CefBrowserHostImpl> browser) {
CefRefPtr<CefBrowserHostBase> browser) {
if (browser) {
const CefBrowserSettings& browser_settings = browser->settings();
if (browser_settings.accept_language_list.length > 0) {
@ -163,10 +163,10 @@ class InterceptedRequestHandlerWrapper : public InterceptedRequestHandler {
// Observer to receive notification of CEF context or associated browser
// destruction. Only one of the *Destroyed() methods will be called.
class DestructionObserver : public CefBrowserHostImpl::Observer,
class DestructionObserver : public CefBrowserHostBase::Observer,
public CefContext::Observer {
public:
explicit DestructionObserver(CefBrowserHostImpl* browser) {
explicit DestructionObserver(CefBrowserHostBase* browser) {
if (browser) {
browser_info_ = browser->browser_info();
browser->AddObserver(this);
@ -198,7 +198,7 @@ class InterceptedRequestHandlerWrapper : public InterceptedRequestHandler {
wrapper_ = wrapper;
}
void OnBrowserDestroyed(CefBrowserHostImpl* browser) override {
void OnBrowserDestroyed(CefBrowserHostBase* browser) override {
CEF_REQUIRE_UIT();
browser->RemoveObserver(this);
registered_ = false;
@ -249,7 +249,7 @@ class InterceptedRequestHandlerWrapper : public InterceptedRequestHandler {
}
void Initialize(content::BrowserContext* browser_context,
CefRefPtr<CefBrowserHostImpl> browser,
CefRefPtr<CefBrowserHostBase> browser,
CefRefPtr<CefFrame> frame,
int render_process_id,
int render_frame_id,
@ -310,7 +310,7 @@ class InterceptedRequestHandlerWrapper : public InterceptedRequestHandler {
bool initialized_ = false;
CefRefPtr<CefBrowserHostImpl> browser_;
CefRefPtr<CefBrowserHostBase> browser_;
CefRefPtr<CefFrame> frame_;
CefIOThreadState* iothread_state_ = nullptr;
CefBrowserContext::CookieableSchemes cookieable_schemes_;
@ -1239,13 +1239,13 @@ void InitOnUIThread(
}
}
CefRefPtr<CefBrowserHostImpl> browserPtr;
CefRefPtr<CefBrowserHostBase> browserPtr;
CefRefPtr<CefFrame> framePtr;
// |frame| may be null for service worker requests.
if (frame) {
// May return nullptr for requests originating from guest views.
browserPtr = CefBrowserHostImpl::GetBrowserForHost(frame);
browserPtr = CefBrowserHostBase::GetBrowserForHost(frame);
if (browserPtr) {
framePtr = browserPtr->GetFrameForHost(frame);
if (frame_tree_node_id < 0)
@ -1282,7 +1282,7 @@ std::unique_ptr<InterceptedRequestHandler> CreateInterceptedRequestHandler(
bool is_download,
const url::Origin& request_initiator) {
CEF_REQUIRE_UIT();
CefRefPtr<CefBrowserHostImpl> browserPtr;
CefRefPtr<CefBrowserHostBase> browserPtr;
CefRefPtr<CefFrame> framePtr;
int render_frame_id = -1;
int frame_tree_node_id = -1;
@ -1293,7 +1293,7 @@ std::unique_ptr<InterceptedRequestHandler> CreateInterceptedRequestHandler(
frame_tree_node_id = frame->GetFrameTreeNodeId();
// May return nullptr for requests originating from guest views.
browserPtr = CefBrowserHostImpl::GetBrowserForHost(frame);
browserPtr = CefBrowserHostBase::GetBrowserForHost(frame);
if (browserPtr) {
framePtr = browserPtr->GetFrameForHost(frame);
DCHECK(framePtr);

View File

@ -6,10 +6,12 @@
#include <string>
#include "libcef/browser/browser_host_impl.h"
#include "libcef/browser/context.h"
#include "libcef/browser/extensions/browser_extensions_util.h"
#include "libcef/common/cef_switches.h"
#include "libcef/common/extensions/extensions_util.h"
#include "libcef/features/runtime_checks.h"
#include "base/command_line.h"
#include "base/i18n/character_encoding.h"
@ -349,8 +351,9 @@ void RegisterProfilePrefs(user_prefs::PrefRegistrySyncable* registry,
void PopulateWebPreferences(content::RenderViewHost* rvh,
content::WebPreferences& web) {
CefRefPtr<CefBrowserHostImpl> browser =
extensions::GetOwnerBrowserForHost(rvh, nullptr);
REQUIRE_ALLOY_RUNTIME();
CefRefPtr<CefBrowserHostImpl> browser = static_cast<CefBrowserHostImpl*>(
extensions::GetOwnerBrowserForHost(rvh, nullptr).get());
// Set defaults for preferences that are not handled by PrefService.
SetDefaultPrefs(web);

View File

@ -149,9 +149,8 @@ void CefPrintDialogLinux::OnPrintStart(int render_process_id,
if (!handler.get())
return;
CefRefPtr<CefBrowserHostImpl> browser =
extensions::GetOwnerBrowserForFrameRoute(render_process_id,
render_routing_id, nullptr);
auto browser = extensions::GetOwnerBrowserForFrameRoute(
render_process_id, render_routing_id, nullptr);
if (browser.get())
handler->OnPrintStart(browser.get());
}

View File

@ -7,7 +7,7 @@
#define LIBCEF_BROWSER_PRINTING_PRINT_DIALOG_LINUX_H_
#include "include/cef_print_handler.h"
#include "libcef/browser/browser_host_impl.h"
#include "libcef/browser/browser_host_base.h"
#include "base/compiler_specific.h"
#include "base/files/file_path.h"
@ -87,7 +87,7 @@ class CefPrintDialogLinux : public printing::PrintDialogGtkInterface,
// Printing dialog callback.
PrintingContextLinux::PrintSettingsCallback callback_;
PrintingContextLinux* context_;
CefRefPtr<CefBrowserHostImpl> browser_;
CefRefPtr<CefBrowserHostBase> browser_;
base::FilePath path_to_pdf_;

View File

@ -188,7 +188,7 @@ void CefBrowserViewImpl::SetPendingBrowserCreateParams(
CefRefPtr<CefDictionaryValue> extra_info,
CefRefPtr<CefRequestContext> request_context) {
DCHECK(!pending_browser_create_params_);
pending_browser_create_params_.reset(new CefBrowserHostImpl::CreateParams());
pending_browser_create_params_.reset(new CefBrowserHostBase::CreateParams());
pending_browser_create_params_->client = client;
pending_browser_create_params_->url = GURL(url.ToString());
pending_browser_create_params_->settings = settings;

View File

@ -95,7 +95,7 @@ class CefBrowserViewImpl : public CefViewImpl<CefBrowserViewView,
bool HandleAccelerator(const content::NativeWebKeyboardEvent& event,
views::FocusManager* focus_manager);
std::unique_ptr<CefBrowserHostImpl::CreateParams>
std::unique_ptr<CefBrowserHostBase::CreateParams>
pending_browser_create_params_;
CefRefPtr<CefBrowserHostImpl> browser_;

View File

@ -13,6 +13,6 @@
CHECK(cef::IsAlloyRuntimeEnabled()) << "Alloy runtime is required"
#define REQUIRE_CHROME_RUNTIME() \
CHECK(cef::IsChrimeRuntimeEnabled()) << "Chrome runtime is required"
CHECK(cef::IsChromeRuntimeEnabled()) << "Chrome runtime is required"
#endif // CEF_LIBCEF_FEATURES_RUNTIME_CHECKS_H_

View File

@ -9,10 +9,11 @@
// implementations. See the translator.README.txt file in the tools directory
// for more information.
//
// $hash=7f01f5096df081ae224560eefba57b45fb9c758b$
// $hash=94217ee1df26d037136df93adda612261606c569$
//
#include "libcef_dll/cpptoc/browser_process_handler_cpptoc.h"
#include "libcef_dll/cpptoc/client_cpptoc.h"
#include "libcef_dll/cpptoc/print_handler_cpptoc.h"
#include "libcef_dll/ctocpp/command_line_ctocpp.h"
@ -81,6 +82,22 @@ void CEF_CALLBACK browser_process_handler_on_schedule_message_pump_work(
delay_ms);
}
struct _cef_client_t* CEF_CALLBACK browser_process_handler_get_default_client(
struct _cef_browser_process_handler_t* self) {
// AUTO-GENERATED CONTENT - DELETE THIS COMMENT BEFORE MODIFYING
DCHECK(self);
if (!self)
return NULL;
// Execute
CefRefPtr<CefClient> _retval =
CefBrowserProcessHandlerCppToC::Get(self)->GetDefaultClient();
// Return type: refptr_same
return CefClientCppToC::Wrap(_retval);
}
} // namespace
// CONSTRUCTOR - Do not edit by hand.
@ -93,6 +110,7 @@ CefBrowserProcessHandlerCppToC::CefBrowserProcessHandlerCppToC() {
GetStruct()->get_print_handler = browser_process_handler_get_print_handler;
GetStruct()->on_schedule_message_pump_work =
browser_process_handler_on_schedule_message_pump_work;
GetStruct()->get_default_client = browser_process_handler_get_default_client;
}
// DESTRUCTOR - Do not edit by hand.

View File

@ -9,11 +9,12 @@
// implementations. See the translator.README.txt file in the tools directory
// for more information.
//
// $hash=394c9b4009a90393aa15be216b5e44f1bafccdfb$
// $hash=9e8f283905d68b7b97c13a568040dc12c2859ad3$
//
#include "libcef_dll/ctocpp/browser_process_handler_ctocpp.h"
#include "libcef_dll/cpptoc/command_line_cpptoc.h"
#include "libcef_dll/ctocpp/client_ctocpp.h"
#include "libcef_dll/ctocpp/print_handler_ctocpp.h"
// VIRTUAL METHODS - Body may be edited by hand.
@ -76,6 +77,21 @@ void CefBrowserProcessHandlerCToCpp::OnScheduleMessagePumpWork(int64 delay_ms) {
_struct->on_schedule_message_pump_work(_struct, delay_ms);
}
NO_SANITIZE("cfi-icall")
CefRefPtr<CefClient> CefBrowserProcessHandlerCToCpp::GetDefaultClient() {
cef_browser_process_handler_t* _struct = GetStruct();
if (CEF_MEMBER_MISSING(_struct, get_default_client))
return nullptr;
// AUTO-GENERATED CONTENT - DELETE THIS COMMENT BEFORE MODIFYING
// Execute
cef_client_t* _retval = _struct->get_default_client(_struct);
// Return type: refptr_same
return CefClientCToCpp::Wrap(_retval);
}
// CONSTRUCTOR - Do not edit by hand.
CefBrowserProcessHandlerCToCpp::CefBrowserProcessHandlerCToCpp() {}

View File

@ -9,7 +9,7 @@
// implementations. See the translator.README.txt file in the tools directory
// for more information.
//
// $hash=79e6f729e377f1dca76c076d7c694f07b8e171e6$
// $hash=857a8ad51f8b7ca9e62b9ce35d0cf510d84fb8b1$
//
#ifndef CEF_LIBCEF_DLL_CTOCPP_BROWSER_PROCESS_HANDLER_CTOCPP_H_
@ -40,6 +40,7 @@ class CefBrowserProcessHandlerCToCpp
CefRefPtr<CefCommandLine> command_line) override;
CefRefPtr<CefPrintHandler> GetPrintHandler() override;
void OnScheduleMessagePumpWork(int64 delay_ms) override;
CefRefPtr<CefClient> GetDefaultClient() override;
};
#endif // CEF_LIBCEF_DLL_CTOCPP_BROWSER_PROCESS_HANDLER_CTOCPP_H_

View File

@ -217,6 +217,11 @@ patches = [
# https://bitbucket.org/chromiumembedded/cef/issues/2969
'name': 'chrome_runtime',
},
{
# Changes to support the Chrome runtime in CEF.
# https://bitbucket.org/chromiumembedded/cef/issues/2969
'name': 'chrome_browser_browser',
},
{
# Don't initialize ExtensionSystemFactory when extensions are disabled.
# https://bitbucket.org/chromiumembedded/cef/issues/2359

View File

@ -0,0 +1,180 @@
diff --git chrome/browser/ui/browser.cc chrome/browser/ui/browser.cc
index 71ec3bbbf1b6..8b99a3ac7de2 100644
--- chrome/browser/ui/browser.cc
+++ chrome/browser/ui/browser.cc
@@ -257,6 +257,20 @@
#include "components/captive_portal/content/captive_portal_tab_helper.h"
#endif
+#if BUILDFLAG(ENABLE_CEF)
+#define CALL_CEF_DELEGATE(name, ...) \
+ if (cef_browser_delegate_) { \
+ cef_browser_delegate_->name(__VA_ARGS__); \
+ }
+#define CALL_CEF_DELEGATE_RETURN(name, ...) \
+ if (cef_browser_delegate_) { \
+ return cef_browser_delegate_->name(__VA_ARGS__); \
+ }
+#else // !BUILDFLAG(ENABLE_CEF)
+#define CALL_CEF_DELEGATE(name, ...)
+#define CALL_CEF_DELEGATE_RETURN(name, ...)
+#endif
+
#if BUILDFLAG(ENABLE_EXTENSIONS)
#include "chrome/browser/extensions/extension_browser_window_helper.h"
#endif
@@ -470,6 +484,13 @@ Browser::Browser(const CreateParams& params)
CHECK(CanCreateBrowserForProfile(profile_));
+#if BUILDFLAG(ENABLE_CEF)
+ if (cef::IsChromeRuntimeEnabled()) {
+ cef_browser_delegate_ =
+ cef::BrowserDelegate::Create(this, params.cef_params);
+ }
+#endif
+
tab_strip_model_->AddObserver(this);
location_bar_model_ = std::make_unique<LocationBarModelImpl>(
@@ -1713,6 +1734,8 @@ void Browser::LoadingStateChanged(WebContents* source,
bool to_different_document) {
ScheduleUIUpdate(source, content::INVALIDATE_TYPE_LOAD);
UpdateWindowForLoadingStateChanged(source, to_different_document);
+
+ CALL_CEF_DELEGATE(LoadingStateChanged, source, to_different_document);
}
void Browser::CloseContents(WebContents* source) {
@@ -1740,6 +1763,8 @@ void Browser::SetContentsBounds(WebContents* source, const gfx::Rect& bounds) {
}
void Browser::UpdateTargetURL(WebContents* source, const GURL& url) {
+ CALL_CEF_DELEGATE(UpdateTargetURL, source, url);
+
if (!GetStatusBubble())
return;
@@ -1747,6 +1772,17 @@ void Browser::UpdateTargetURL(WebContents* source, const GURL& url) {
GetStatusBubble()->SetURL(url);
}
+bool Browser::DidAddMessageToConsole(
+ content::WebContents* source,
+ blink::mojom::ConsoleMessageLevel log_level,
+ const base::string16& message,
+ int32_t line_no,
+ const base::string16& source_id) {
+ CALL_CEF_DELEGATE_RETURN(DidAddMessageToConsole, source, log_level, message,
+ line_no, source_id);
+ return false;
+}
+
void Browser::ContentsMouseEvent(WebContents* source,
bool motion,
bool exited) {
@@ -1899,6 +1935,8 @@ void Browser::RendererResponsive(
void Browser::DidNavigateMainFramePostCommit(WebContents* web_contents) {
if (web_contents == tab_strip_model_->GetActiveWebContents())
UpdateBookmarkBarState(BOOKMARK_BAR_STATE_CHANGE_TAB_STATE);
+
+ CALL_CEF_DELEGATE(DidNavigateMainFramePostCommit, web_contents);
}
content::JavaScriptDialogManager* Browser::GetJavaScriptDialogManager(
@@ -1949,11 +1987,15 @@ void Browser::EnterFullscreenModeForTab(
const blink::mojom::FullscreenOptions& options) {
exclusive_access_manager_->fullscreen_controller()->EnterFullscreenModeForTab(
requesting_frame, options.display_id);
+
+ CALL_CEF_DELEGATE(EnterFullscreenModeForTab, requesting_frame, options);
}
void Browser::ExitFullscreenModeForTab(WebContents* web_contents) {
exclusive_access_manager_->fullscreen_controller()->ExitFullscreenModeForTab(
web_contents);
+
+ CALL_CEF_DELEGATE(ExitFullscreenModeForTab, web_contents);
}
bool Browser::IsFullscreenForTabOrPending(const WebContents* web_contents) {
@@ -2814,6 +2856,8 @@ void Browser::SetAsDelegate(WebContents* web_contents, bool set_delegate) {
content_translate_driver->RemoveObserver(this);
BookmarkTabHelper::FromWebContents(web_contents)->RemoveObserver(this);
}
+
+ CALL_CEF_DELEGATE(SetAsDelegate, web_contents, set_delegate);
}
void Browser::CloseFrame() {
diff --git chrome/browser/ui/browser.h chrome/browser/ui/browser.h
index ab2a03e6e878..aef94abf4fd8 100644
--- chrome/browser/ui/browser.h
+++ chrome/browser/ui/browser.h
@@ -21,6 +21,7 @@
#include "base/strings/string16.h"
#include "base/timer/elapsed_timer.h"
#include "build/build_config.h"
+#include "cef/libcef/features/runtime.h"
#include "chrome/browser/devtools/devtools_toggle_action.h"
#include "chrome/browser/ui/bookmarks/bookmark_bar.h"
#include "chrome/browser/ui/bookmarks/bookmark_tab_helper_observer.h"
@@ -56,6 +57,10 @@
#include "ui/gfx/geometry/rect.h"
#include "ui/shell_dialogs/select_file_dialog.h"
+#if BUILDFLAG(ENABLE_CEF)
+#include "cef/libcef/browser/chrome/browser_delegate.h"
+#endif
+
#if defined(OS_ANDROID)
#error This file should only be included on desktop.
#endif
@@ -241,6 +246,11 @@ class Browser : public TabStripModelObserver,
// default. Intended for testing.
BrowserWindow* window = nullptr;
+#if BUILDFLAG(ENABLE_CEF)
+ // Opaque CEF-specific configuration. Will be propagated to new Browsers.
+ scoped_refptr<cef::BrowserDelegate::CreateParams> cef_params;
+#endif
+
private:
friend class Browser;
friend class WindowSizerChromeOSTest;
@@ -358,6 +368,12 @@ class Browser : public TabStripModelObserver,
return &signin_view_controller_;
}
+#if BUILDFLAG(ENABLE_CEF)
+ cef::BrowserDelegate* cef_delegate() const {
+ return cef_browser_delegate_.get();
+ }
+#endif
+
// Get the FindBarController for this browser, creating it if it does not
// yet exist.
FindBarController* GetFindBarController();
@@ -742,6 +758,11 @@ class Browser : public TabStripModelObserver,
void SetContentsBounds(content::WebContents* source,
const gfx::Rect& bounds) override;
void UpdateTargetURL(content::WebContents* source, const GURL& url) override;
+ bool DidAddMessageToConsole(content::WebContents* source,
+ blink::mojom::ConsoleMessageLevel log_level,
+ const base::string16& message,
+ int32_t line_no,
+ const base::string16& source_id) override;
void ContentsMouseEvent(content::WebContents* source,
bool motion,
bool exited) override;
@@ -1206,6 +1227,10 @@ class Browser : public TabStripModelObserver,
extension_browser_window_helper_;
#endif
+#if BUILDFLAG(ENABLE_CEF)
+ std::unique_ptr<cef::BrowserDelegate> cef_browser_delegate_;
+#endif
+
const base::ElapsedTimer creation_timer_;
// Stores the list of browser windows showing via a menu.