2020-09-18 00:24:08 +02:00
|
|
|
// 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>
|
|
|
|
|
2021-06-04 03:34:56 +02:00
|
|
|
#include "base/callback_list.h"
|
2020-09-18 00:24:08 +02:00
|
|
|
#include "base/observer_list.h"
|
2024-04-30 17:45:07 +02:00
|
|
|
#include "cef/libcef/browser/frame_host_impl.h"
|
2020-09-18 00:24:08 +02:00
|
|
|
#include "content/public/browser/web_contents_delegate.h"
|
|
|
|
#include "content/public/browser/web_contents_observer.h"
|
|
|
|
|
|
|
|
class CefBrowser;
|
|
|
|
class CefBrowserInfo;
|
2020-09-25 03:40:47 +02:00
|
|
|
class CefBrowserPlatformDelegate;
|
2020-09-18 00:24:08 +02:00
|
|
|
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,
|
2023-12-06 21:16:15 +01:00
|
|
|
public content::WebContentsObserver {
|
2020-09-18 00:24:08 +02:00
|
|
|
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.
|
2020-09-25 03:40:47 +02:00
|
|
|
virtual void OnWebContentsDestroyed(content::WebContents* web_contents) = 0;
|
2020-09-18 00:24:08 +02:00
|
|
|
|
|
|
|
protected:
|
2024-01-20 23:48:57 +01:00
|
|
|
~Observer() override = default;
|
2020-09-18 00:24:08 +02:00
|
|
|
};
|
|
|
|
|
|
|
|
explicit CefBrowserContentsDelegate(
|
|
|
|
scoped_refptr<CefBrowserInfo> browser_info);
|
|
|
|
|
2021-12-06 21:40:25 +01:00
|
|
|
CefBrowserContentsDelegate(const CefBrowserContentsDelegate&) = delete;
|
|
|
|
CefBrowserContentsDelegate& operator=(const CefBrowserContentsDelegate&) =
|
|
|
|
delete;
|
|
|
|
|
2020-09-18 00:24:08 +02:00
|
|
|
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);
|
|
|
|
|
2024-04-23 22:06:00 +02:00
|
|
|
// Same as OpenURLFromTab but only taking |navigation_handle_callback|
|
|
|
|
// if the return value is non-nullptr.
|
|
|
|
content::WebContents* OpenURLFromTabEx(
|
2020-09-25 03:40:47 +02:00
|
|
|
content::WebContents* source,
|
2024-04-23 22:06:00 +02:00
|
|
|
const content::OpenURLParams& params,
|
|
|
|
base::OnceCallback<void(content::NavigationHandle&)>&
|
|
|
|
navigation_handle_callback);
|
|
|
|
|
|
|
|
// WebContentsDelegate methods:
|
2020-09-18 00:24:08 +02:00
|
|
|
void LoadingStateChanged(content::WebContents* source,
|
2021-12-16 23:35:54 +01:00
|
|
|
bool should_show_loading_ui) override;
|
2020-09-18 00:24:08 +02:00
|
|
|
void UpdateTargetURL(content::WebContents* source, const GURL& url) override;
|
|
|
|
bool DidAddMessageToConsole(content::WebContents* source,
|
|
|
|
blink::mojom::ConsoleMessageLevel log_level,
|
2021-04-21 00:52:34 +02:00
|
|
|
const std::u16string& message,
|
2020-09-18 00:24:08 +02:00
|
|
|
int32_t line_no,
|
2021-04-21 00:52:34 +02:00
|
|
|
const std::u16string& source_id) override;
|
2020-09-18 00:24:08 +02:00
|
|
|
void EnterFullscreenModeForTab(
|
|
|
|
content::RenderFrameHost* requesting_frame,
|
|
|
|
const blink::mojom::FullscreenOptions& options) override;
|
|
|
|
void ExitFullscreenModeForTab(content::WebContents* web_contents) override;
|
2022-03-22 22:40:28 +01:00
|
|
|
void CanDownload(const GURL& url,
|
|
|
|
const std::string& request_method,
|
|
|
|
base::OnceCallback<void(bool)> callback) override;
|
2020-09-25 03:40:47 +02:00
|
|
|
content::KeyboardEventProcessingResult PreHandleKeyboardEvent(
|
|
|
|
content::WebContents* source,
|
|
|
|
const content::NativeWebKeyboardEvent& event) override;
|
|
|
|
bool HandleKeyboardEvent(
|
|
|
|
content::WebContents* source,
|
|
|
|
const content::NativeWebKeyboardEvent& event) override;
|
2024-04-23 22:06:00 +02:00
|
|
|
void DraggableRegionsChanged(
|
|
|
|
const std::vector<blink::mojom::DraggableRegionPtr>& regions,
|
|
|
|
content::WebContents* contents) override;
|
2020-09-18 00:24:08 +02:00
|
|
|
|
|
|
|
// WebContentsObserver methods:
|
|
|
|
void RenderFrameCreated(content::RenderFrameHost* render_frame_host) override;
|
|
|
|
void RenderFrameHostChanged(content::RenderFrameHost* old_host,
|
|
|
|
content::RenderFrameHost* new_host) override;
|
2021-07-25 19:31:39 +02:00
|
|
|
void RenderFrameHostStateChanged(
|
|
|
|
content::RenderFrameHost* host,
|
|
|
|
content::RenderFrameHost::LifecycleState old_state,
|
|
|
|
content::RenderFrameHost::LifecycleState new_state) override;
|
2020-09-18 00:24:08 +02:00
|
|
|
void RenderFrameDeleted(content::RenderFrameHost* render_frame_host) override;
|
2022-04-14 01:35:46 +02:00
|
|
|
void RenderWidgetCreated(
|
|
|
|
content::RenderWidgetHost* render_widget_host) override;
|
2020-09-18 00:24:08 +02:00
|
|
|
void RenderViewReady() override;
|
2021-11-10 22:57:31 +01:00
|
|
|
void PrimaryMainFrameRenderProcessGone(
|
|
|
|
base::TerminationStatus status) override;
|
2020-09-18 00:24:08 +02:00
|
|
|
void OnFrameFocused(content::RenderFrameHost* render_frame_host) override;
|
2022-02-21 23:23:40 +01:00
|
|
|
void PrimaryMainDocumentElementAvailable() override;
|
2020-09-18 00:24:08 +02:00
|
|
|
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;
|
2022-08-26 00:17:51 +02:00
|
|
|
void DidFinishLoad(content::RenderFrameHost* render_frame_host,
|
|
|
|
const GURL& validated_url) override;
|
2020-09-18 00:24:08 +02:00
|
|
|
void TitleWasSet(content::NavigationEntry* entry) override;
|
|
|
|
void DidUpdateFaviconURL(
|
|
|
|
content::RenderFrameHost* render_frame_host,
|
|
|
|
const std::vector<blink::mojom::FaviconURLPtr>& candidates) override;
|
|
|
|
void OnWebContentsFocused(
|
|
|
|
content::RenderWidgetHost* render_widget_host) override;
|
2021-06-04 03:34:56 +02:00
|
|
|
void OnFocusChangedInPage(content::FocusedNodeDetails* details) override;
|
2020-09-18 00:24:08 +02:00
|
|
|
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.
|
2020-09-25 03:40:47 +02:00
|
|
|
// TODO(cef): Make this private if/when possible.
|
|
|
|
bool OnSetFocus(cef_focus_source_t source);
|
2020-09-18 00:24:08 +02:00
|
|
|
|
|
|
|
private:
|
|
|
|
CefRefPtr<CefClient> client() const;
|
|
|
|
CefRefPtr<CefBrowser> browser() const;
|
2020-09-25 03:40:47 +02:00
|
|
|
CefBrowserPlatformDelegate* platform_delegate() const;
|
2020-09-18 00:24:08 +02:00
|
|
|
|
2020-09-25 03:40:47 +02:00
|
|
|
// Helpers for executing client callbacks.
|
|
|
|
void OnAddressChange(const GURL& url);
|
|
|
|
void OnLoadStart(CefRefPtr<CefFrame> frame,
|
|
|
|
ui::PageTransition transition_type);
|
2022-08-26 00:17:51 +02:00
|
|
|
void OnLoadEnd(CefRefPtr<CefFrame> frame,
|
|
|
|
const GURL& url,
|
|
|
|
int http_status_code);
|
2020-09-25 03:40:47 +02:00
|
|
|
void OnLoadError(CefRefPtr<CefFrame> frame, const GURL& url, int error_code);
|
2021-04-21 00:52:34 +02:00
|
|
|
void OnTitleChange(const std::u16string& title);
|
2020-09-18 00:24:08 +02:00
|
|
|
void OnFullscreenModeChange(bool fullscreen);
|
2020-09-25 03:40:47 +02:00
|
|
|
|
2020-09-18 00:24:08 +02:00
|
|
|
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_;
|
|
|
|
|
2020-09-25 03:40:47 +02:00
|
|
|
// True if currently in the OnSetFocus callback.
|
|
|
|
bool is_in_onsetfocus_ = false;
|
|
|
|
|
2020-09-18 00:24:08 +02:00
|
|
|
// Observers that want to be notified of changes to this object.
|
|
|
|
base::ObserverList<Observer> observers_;
|
|
|
|
|
2020-09-25 03:40:47 +02:00
|
|
|
// True if the focus is currently on an editable field on the page.
|
|
|
|
bool focus_on_editable_field_ = false;
|
2020-09-18 00:24:08 +02:00
|
|
|
};
|
|
|
|
|
|
|
|
#endif // CEF_LIBCEF_BROWSER_BROWSER_CONTENTS_DELEGATE_H_
|