Skip to content

Commit

Permalink
Add new CanZoom/Zoom API (fixes #3284)
Browse files Browse the repository at this point in the history
Add a simpler CanZoom/Zoom API as an alternative to the more error-prone
SetZoomLevel/GetZoomLevel API. Both APIs are now implemented for both runtimes.
With the Chrome runtime a zoom notification bubble will be displayed unless
CefBrowserSettings.chrome_zoom_bubble is set to STATE_DISABLED.

To test:
- Run cefclient and select zoom entries from the Tests menu.
- chrome: Run cefclient with `--hide-chrome-bubbles` command-line flag to hide
  the zoom notification bubble.
  • Loading branch information
magreenblatt committed Oct 5, 2023
1 parent 238aa32 commit 721b365
Show file tree
Hide file tree
Showing 20 changed files with 338 additions and 80 deletions.
35 changes: 29 additions & 6 deletions include/capi/cef_browser_capi.h
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@
// by hand. See the translator.README.txt file in the tools directory for
// more information.
//
// $hash=683d7bff8da04826eee83c7e23cf9c5a701ae265$
// $hash=db4fce1215cb4f69346ef2d048974ba34187b2b1$
//

#ifndef CEF_INCLUDE_CAPI_CEF_BROWSER_CAPI_H_
Expand Down Expand Up @@ -365,16 +365,39 @@ typedef struct _cef_browser_host_t {
struct _cef_browser_host_t* self);

///
/// Get the current zoom level. The default zoom level is 0.0. This function
/// can only be called on the UI thread.
/// Returns true (1) if this browser can execute the specified zoom command.
/// This function can only be called on the UI thread.
///
int(CEF_CALLBACK* can_zoom)(struct _cef_browser_host_t* self,
cef_zoom_command_t command);

///
/// Execute a zoom command in this browser. If called on the UI thread the
/// change will be applied immediately. Otherwise, the change will be applied
/// asynchronously on the UI thread.
///
void(CEF_CALLBACK* zoom)(struct _cef_browser_host_t* self,
cef_zoom_command_t command);

///
/// Get the default zoom level. This value will be 0.0 by default but can be
/// configured with the Chrome runtime. This function can only be called on
/// the UI thread.
///
double(CEF_CALLBACK* get_default_zoom_level)(
struct _cef_browser_host_t* self);

///
/// Get the current zoom level. This function can only be called on the UI
/// thread.
///
double(CEF_CALLBACK* get_zoom_level)(struct _cef_browser_host_t* self);

///
/// Change the zoom level to the specified value. Specify 0.0 to reset the
/// zoom level. If called on the UI thread the change will be applied
/// immediately. Otherwise, the change will be applied asynchronously on the
/// UI thread.
/// zoom level to the default. If called on the UI thread the change will be
/// applied immediately. Otherwise, the change will be applied asynchronously
/// on the UI thread.
///
void(CEF_CALLBACK* set_zoom_level)(struct _cef_browser_host_t* self,
double zoomLevel);
Expand Down
8 changes: 4 additions & 4 deletions include/cef_api_hash.h
Original file line number Diff line number Diff line change
Expand Up @@ -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 "fb95812349ecedc56374e2d195b4af712f6f9ab3"
#define CEF_API_HASH_UNIVERSAL "abeac9ee5411570f5e39d9242cba575a19439f86"
#if defined(OS_WIN)
#define CEF_API_HASH_PLATFORM "4b12d27bf02871c32719580c1be18d686e20bc84"
#define CEF_API_HASH_PLATFORM "85fba672bea98e3687ccfc28c4a509ca70240990"
#elif defined(OS_MAC)
#define CEF_API_HASH_PLATFORM "e6b30ef107ccb6ba9af40bd6498ad4cef247a171"
#define CEF_API_HASH_PLATFORM "3c960598536b6e112d3857d19d01f05e49474f86"
#elif defined(OS_LINUX)
#define CEF_API_HASH_PLATFORM "a4ec73cc821ea2d1681c7f8271f0a7d3e3cea33a"
#define CEF_API_HASH_PLATFORM "821845ef5f7ea8618f7425a4096702205f4b346b"
#endif

#ifdef __cplusplus
Expand Down
33 changes: 28 additions & 5 deletions include/cef_browser.h
Original file line number Diff line number Diff line change
Expand Up @@ -396,17 +396,40 @@ class CefBrowserHost : public virtual CefBaseRefCounted {
virtual CefRefPtr<CefRequestContext> GetRequestContext() = 0;

///
/// Get the current zoom level. The default zoom level is 0.0. This method can
/// only be called on the UI thread.
/// Returns true if this browser can execute the specified zoom command. This
/// method can only be called on the UI thread.
///
/*--cef()--*/
virtual bool CanZoom(cef_zoom_command_t command) = 0;

///
/// Execute a zoom command in this browser. If called on the UI thread the
/// change will be applied immediately. Otherwise, the change will be applied
/// asynchronously on the UI thread.
///
/*--cef()--*/
virtual void Zoom(cef_zoom_command_t command) = 0;

///
/// Get the default zoom level. This value will be 0.0 by default but can be
/// configured with the Chrome runtime. This method can only be called on the
/// UI thread.
///
/*--cef()--*/
virtual double GetDefaultZoomLevel() = 0;

///
/// Get the current zoom level. This method can only be called on the UI
/// thread.
///
/*--cef()--*/
virtual double GetZoomLevel() = 0;

///
/// Change the zoom level to the specified value. Specify 0.0 to reset the
/// zoom level. If called on the UI thread the change will be applied
/// immediately. Otherwise, the change will be applied asynchronously on the
/// UI thread.
/// zoom level to the default. If called on the UI thread the change will be
/// applied immediately. Otherwise, the change will be applied asynchronously
/// on the UI thread.
///
/*--cef()--*/
virtual void SetZoomLevel(double zoomLevel) = 0;
Expand Down
15 changes: 15 additions & 0 deletions include/internal/cef_types.h
Original file line number Diff line number Diff line change
Expand Up @@ -687,6 +687,12 @@ typedef struct _cef_browser_settings_t {
/// https://www.chromium.org/user-experience/status-bubble/
///
cef_state_t chrome_status_bubble;

///
/// Controls whether the Chrome zoom bubble will be shown when zooming. Only
/// supported with the Chrome runtime.
///
cef_state_t chrome_zoom_bubble;
} cef_browser_settings_t;

///
Expand Down Expand Up @@ -3660,6 +3666,15 @@ typedef enum {
CEF_GESTURE_COMMAND_FORWARD,
} cef_gesture_command_t;

///
/// Specifies the zoom commands supported by CefBrowserHost::Zoom.
///
typedef enum {
CEF_ZOOM_COMMAND_OUT,
CEF_ZOOM_COMMAND_RESET,
CEF_ZOOM_COMMAND_IN,
} cef_zoom_command_t;

#ifdef __cplusplus
}
#endif
Expand Down
1 change: 1 addition & 0 deletions include/internal/cef_types_wrappers.h
Original file line number Diff line number Diff line change
Expand Up @@ -541,6 +541,7 @@ struct CefBrowserSettingsTraits {
&target->accept_language_list, copy);

target->chrome_status_bubble = src->chrome_status_bubble;
target->chrome_zoom_bubble = src->chrome_zoom_bubble;
}
};

Expand Down
32 changes: 6 additions & 26 deletions libcef/browser/alloy/alloy_browser_host_impl.cc
Original file line number Diff line number Diff line change
Expand Up @@ -34,10 +34,10 @@
#include "base/functional/callback_helpers.h"
#include "chrome/browser/file_select_helper.h"
#include "chrome/browser/picture_in_picture/picture_in_picture_window_manager.h"
#include "components/zoom/page_zoom.h"
#include "content/browser/gpu/compositor_util.h"
#include "content/public/browser/desktop_media_id.h"
#include "content/public/browser/file_select_listener.h"
#include "content/public/browser/host_zoom_map.h"
#include "content/public/browser/keyboard_event_processing_result.h"
#include "content/public/browser/navigation_controller.h"
#include "content/public/browser/navigation_handle.h"
Expand Down Expand Up @@ -330,31 +330,6 @@ CefWindowHandle AlloyBrowserHostImpl::GetOpenerWindowHandle() {
return opener_;
}

double AlloyBrowserHostImpl::GetZoomLevel() {
// Verify that this method is being called on the UI thread.
if (!CEF_CURRENTLY_ON_UIT()) {
DCHECK(false) << "called on invalid thread";
return 0;
}

if (web_contents()) {
return content::HostZoomMap::GetZoomLevel(web_contents());
}

return 0;
}

void AlloyBrowserHostImpl::SetZoomLevel(double zoomLevel) {
if (CEF_CURRENTLY_ON_UIT()) {
if (web_contents()) {
content::HostZoomMap::SetZoomLevel(web_contents(), zoomLevel);
}
} else {
CEF_POST_TASK(CEF_UIT, base::BindOnce(&AlloyBrowserHostImpl::SetZoomLevel,
this, zoomLevel));
}
}

void AlloyBrowserHostImpl::Find(const CefString& searchText,
bool forward,
bool matchCase,
Expand Down Expand Up @@ -1118,6 +1093,11 @@ bool AlloyBrowserHostImpl::DidAddMessageToConsole(
line_no, source_id);
}

void AlloyBrowserHostImpl::ContentsZoomChange(bool zoom_in) {
zoom::PageZoom::Zoom(
web_contents(), zoom_in ? content::PAGE_ZOOM_IN : content::PAGE_ZOOM_OUT);
}

void AlloyBrowserHostImpl::BeforeUnloadFired(content::WebContents* source,
bool proceed,
bool* proceed_to_fire_unload) {
Expand Down
3 changes: 1 addition & 2 deletions libcef/browser/alloy/alloy_browser_host_impl.h
Original file line number Diff line number Diff line change
Expand Up @@ -80,8 +80,6 @@ class AlloyBrowserHostImpl : public CefBrowserHostBase,
bool TryCloseBrowser() override;
CefWindowHandle GetWindowHandle() override;
CefWindowHandle GetOpenerWindowHandle() override;
double GetZoomLevel() override;
void SetZoomLevel(double zoomLevel) override;
void Find(const CefString& searchText,
bool forward,
bool matchCase,
Expand Down Expand Up @@ -204,6 +202,7 @@ class AlloyBrowserHostImpl : public CefBrowserHostBase,
const std::u16string& message,
int32_t line_no,
const std::u16string& source_id) override;
void ContentsZoomChange(bool zoom_in) override;
void BeforeUnloadFired(content::WebContents* source,
bool proceed,
bool* proceed_to_fire_unload) override;
Expand Down
6 changes: 1 addition & 5 deletions libcef/browser/alloy/browser_platform_delegate_alloy.cc
Original file line number Diff line number Diff line change
Expand Up @@ -171,11 +171,7 @@ void CefBrowserPlatformDelegateAlloy::BrowserCreated(
permissions::PermissionRequestManager::CreateForWebContents(web_contents_);
PrefsTabHelper::CreateForWebContents(web_contents_);
printing::PrintViewManager::CreateForWebContents(web_contents_);

if (extensions::ExtensionsEnabled()) {
// Used by the tabs extension API.
zoom::ZoomController::CreateForWebContents(web_contents_);
}
zoom::ZoomController::CreateForWebContents(web_contents_);

javascript_dialogs::TabModalDialogManager::CreateForWebContents(
web_contents_,
Expand Down
105 changes: 105 additions & 0 deletions libcef/browser/browser_host_base.cc
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,10 @@
#include "chrome/browser/platform_util.h"
#include "chrome/browser/spellchecker/spellcheck_factory.h"
#include "chrome/browser/spellchecker/spellcheck_service.h"
#include "chrome/browser/ui/browser_commands.cc"
#include "components/favicon/core/favicon_url.h"
#include "components/spellcheck/common/spellcheck_features.h"
#include "components/zoom/page_zoom.h"
#include "content/browser/renderer_host/render_frame_host_impl.h"
#include "content/public/browser/browser_context.h"
#include "content/public/browser/download_manager.h"
Expand Down Expand Up @@ -236,6 +238,109 @@ CefRefPtr<CefRequestContext> CefBrowserHostBase::GetRequestContext() {
return request_context_;
}

bool CefBrowserHostBase::CanZoom(cef_zoom_command_t command) {
// Verify that this method is being called on the UI thread.
if (!CEF_CURRENTLY_ON_UIT()) {
DCHECK(false) << "called on invalid thread";
return false;
}

if (auto web_contents = GetWebContents()) {
switch (command) {
case CEF_ZOOM_COMMAND_OUT:
return chrome::CanZoomOut(web_contents);
case CEF_ZOOM_COMMAND_RESET:
return chrome::CanResetZoom(web_contents);
case CEF_ZOOM_COMMAND_IN:
return chrome::CanZoomIn(web_contents);
}
}

return false;
}

void CefBrowserHostBase::Zoom(cef_zoom_command_t command) {
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(CEF_UIT,
base::BindOnce(&CefBrowserHostBase::Zoom, this, command));
return;
}

if (auto web_contents = GetWebContents()) {
const content::PageZoom page_zoom = [command]() {
switch (command) {
case CEF_ZOOM_COMMAND_OUT:
return content::PAGE_ZOOM_OUT;
case CEF_ZOOM_COMMAND_RESET:
return content::PAGE_ZOOM_RESET;
case CEF_ZOOM_COMMAND_IN:
return content::PAGE_ZOOM_IN;
}
}();

// Same implementation as chrome::Zoom(), but explicitly specifying the
// WebContents.
zoom::PageZoom::Zoom(web_contents, page_zoom);
}
}

double CefBrowserHostBase::GetDefaultZoomLevel() {
// Verify that this method is being called on the UI thread.
if (!CEF_CURRENTLY_ON_UIT()) {
DCHECK(false) << "called on invalid thread";
return 0.0;
}

if (auto web_contents = GetWebContents()) {
zoom::ZoomController* zoom_controller =
zoom::ZoomController::FromWebContents(web_contents);
if (zoom_controller) {
return zoom_controller->GetDefaultZoomLevel();
}
}

return 0.0;
}

double CefBrowserHostBase::GetZoomLevel() {
// Verify that this method is being called on the UI thread.
if (!CEF_CURRENTLY_ON_UIT()) {
DCHECK(false) << "called on invalid thread";
return 0.0;
}

if (auto web_contents = GetWebContents()) {
zoom::ZoomController* zoom_controller =
zoom::ZoomController::FromWebContents(web_contents);
if (zoom_controller) {
return zoom_controller->GetZoomLevel();
}
}

return 0.0;
}

void CefBrowserHostBase::SetZoomLevel(double zoomLevel) {
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(CEF_UIT, base::BindOnce(&CefBrowserHostBase::SetZoomLevel,
this, zoomLevel));
return;
}

if (auto web_contents = GetWebContents()) {
zoom::ZoomController* zoom_controller =
zoom::ZoomController::FromWebContents(web_contents);
if (zoom_controller) {
if (zoomLevel == 0.0) {
// Same logic as PageZoom::Zoom(PAGE_ZOOM_RESET).
zoomLevel = zoom_controller->GetDefaultZoomLevel();
web_contents->SetPageScale(1.f);
}
zoom_controller->SetZoomLevel(zoomLevel);
}
}
}

bool CefBrowserHostBase::HasView() {
return is_views_hosted_;
}
Expand Down
5 changes: 5 additions & 0 deletions libcef/browser/browser_host_base.h
Original file line number Diff line number Diff line change
Expand Up @@ -169,6 +169,11 @@ class CefBrowserHostBase : public CefBrowserHost,
CefRefPtr<CefBrowser> GetBrowser() override;
CefRefPtr<CefClient> GetClient() override;
CefRefPtr<CefRequestContext> GetRequestContext() override;
bool CanZoom(cef_zoom_command_t command) override;
void Zoom(cef_zoom_command_t command) override;
double GetDefaultZoomLevel() override;
double GetZoomLevel() override;
void SetZoomLevel(double zoomLevel) override;
bool HasView() override;
void SetFocus(bool focus) override;
void RunFileDialog(FileDialogMode mode,
Expand Down
9 changes: 0 additions & 9 deletions libcef/browser/chrome/chrome_browser_host_impl.cc
Original file line number Diff line number Diff line change
Expand Up @@ -179,15 +179,6 @@ CefWindowHandle ChromeBrowserHostImpl::GetOpenerWindowHandle() {
return kNullWindowHandle;
}

double ChromeBrowserHostImpl::GetZoomLevel() {
NOTIMPLEMENTED();
return 0.0;
}

void ChromeBrowserHostImpl::SetZoomLevel(double zoomLevel) {
NOTIMPLEMENTED();
}

void ChromeBrowserHostImpl::Find(const CefString& searchText,
bool forward,
bool matchCase,
Expand Down
2 changes: 0 additions & 2 deletions libcef/browser/chrome/chrome_browser_host_impl.h
Original file line number Diff line number Diff line change
Expand Up @@ -67,8 +67,6 @@ class ChromeBrowserHostImpl : public CefBrowserHostBase {
bool TryCloseBrowser() override;
CefWindowHandle GetWindowHandle() override;
CefWindowHandle GetOpenerWindowHandle() override;
double GetZoomLevel() override;
void SetZoomLevel(double zoomLevel) override;
void Find(const CefString& searchText,
bool forward,
bool matchCase,
Expand Down
Loading

0 comments on commit 721b365

Please sign in to comment.