Add initial Viz implementation for OSR (see issue #2575).
The old shared surface implementation has been removed and will need to be re-implemented using the Viz code path.
This commit is contained in:
parent
cc0db5f166
commit
ac2cc54e13
7
BUILD.gn
7
BUILD.gn
|
@ -423,6 +423,8 @@ static_library("libcef_static") {
|
|||
"libcef/browser/origin_whitelist_impl.h",
|
||||
"libcef/browser/osr/browser_platform_delegate_osr.cc",
|
||||
"libcef/browser/osr/browser_platform_delegate_osr.h",
|
||||
"libcef/browser/osr/host_display_client_osr.cc",
|
||||
"libcef/browser/osr/host_display_client_osr.h",
|
||||
"libcef/browser/osr/motion_event_osr.cc",
|
||||
"libcef/browser/osr/motion_event_osr.h",
|
||||
"libcef/browser/osr/osr_accessibility_util.cc",
|
||||
|
@ -431,10 +433,10 @@ static_library("libcef_static") {
|
|||
"libcef/browser/osr/osr_util.h",
|
||||
"libcef/browser/osr/render_widget_host_view_osr.cc",
|
||||
"libcef/browser/osr/render_widget_host_view_osr.h",
|
||||
"libcef/browser/osr/software_output_device_osr.cc",
|
||||
"libcef/browser/osr/software_output_device_osr.h",
|
||||
"libcef/browser/osr/synthetic_gesture_target_osr.cc",
|
||||
"libcef/browser/osr/synthetic_gesture_target_osr.h",
|
||||
"libcef/browser/osr/video_consumer_osr.cc",
|
||||
"libcef/browser/osr/video_consumer_osr.h",
|
||||
"libcef/browser/osr/web_contents_view_osr.cc",
|
||||
"libcef/browser/osr/web_contents_view_osr.h",
|
||||
"libcef/browser/path_util_impl.cc",
|
||||
|
@ -825,7 +827,6 @@ static_library("libcef_static") {
|
|||
"libcef/browser/native/menu_runner_mac.mm",
|
||||
"libcef/browser/osr/browser_platform_delegate_osr_mac.h",
|
||||
"libcef/browser/osr/browser_platform_delegate_osr_mac.mm",
|
||||
"libcef/browser/osr/render_widget_host_view_osr_mac.mm",
|
||||
"libcef/common/util_mac.h",
|
||||
"libcef/common/util_mac.mm",
|
||||
]
|
||||
|
|
|
@ -6,16 +6,16 @@
|
|||
#include "libcef/browser/native/window_x11.h"
|
||||
#include "libcef/browser/thread_util.h"
|
||||
|
||||
#include <X11/Xatom.h>
|
||||
#include <X11/Xlib.h>
|
||||
#include <X11/Xutil.h>
|
||||
#include <X11/extensions/XInput2.h>
|
||||
|
||||
#include "ui/base/x/x11_util.h"
|
||||
#include "ui/events/platform/platform_event_source.h"
|
||||
#include "ui/views/widget/desktop_aura/desktop_window_tree_host_x11.h"
|
||||
#include "ui/views/widget/desktop_aura/x11_topmost_window_finder.h"
|
||||
|
||||
#include <X11/Xatom.h>
|
||||
#include <X11/Xlib.h>
|
||||
#include <X11/Xutil.h>
|
||||
#include <X11/extensions/XInput2.h>
|
||||
|
||||
namespace {
|
||||
|
||||
const char kAtom[] = "ATOM";
|
||||
|
|
|
@ -0,0 +1,155 @@
|
|||
// Copyright 2019 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/osr/host_display_client_osr.h"
|
||||
|
||||
#include <utility>
|
||||
|
||||
#include "libcef/browser/browser_host_impl.h"
|
||||
#include "libcef/browser/osr/render_widget_host_view_osr.h"
|
||||
|
||||
#include "base/memory/shared_memory.h"
|
||||
#include "components/viz/common/resources/resource_format.h"
|
||||
#include "components/viz/common/resources/resource_sizes.h"
|
||||
#include "mojo/public/cpp/system/platform_handle.h"
|
||||
#include "services/viz/privileged/interfaces/compositing/layered_window_updater.mojom.h"
|
||||
#include "skia/ext/platform_canvas.h"
|
||||
#include "third_party/skia/include/core/SkColor.h"
|
||||
#include "third_party/skia/include/core/SkRect.h"
|
||||
#include "third_party/skia/src/core/SkDevice.h"
|
||||
#include "ui/gfx/skia_util.h"
|
||||
|
||||
#if defined(OS_WIN)
|
||||
#include "skia/ext/skia_utils_win.h"
|
||||
#endif
|
||||
|
||||
class CefLayeredWindowUpdaterOSR : public viz::mojom::LayeredWindowUpdater {
|
||||
public:
|
||||
CefLayeredWindowUpdaterOSR(CefRenderWidgetHostViewOSR* const view,
|
||||
viz::mojom::LayeredWindowUpdaterRequest request);
|
||||
~CefLayeredWindowUpdaterOSR() override;
|
||||
|
||||
void SetActive(bool active);
|
||||
const void* GetPixelMemory() const;
|
||||
gfx::Size GetPixelSize() const;
|
||||
|
||||
// viz::mojom::LayeredWindowUpdater implementation.
|
||||
void OnAllocatedSharedMemory(
|
||||
const gfx::Size& pixel_size,
|
||||
mojo::ScopedSharedBufferHandle scoped_buffer_handle) override;
|
||||
void Draw(const gfx::Rect& damage_rect, DrawCallback draw_callback) override;
|
||||
|
||||
private:
|
||||
CefRenderWidgetHostViewOSR* const view_;
|
||||
mojo::Binding<viz::mojom::LayeredWindowUpdater> binding_;
|
||||
bool active_ = false;
|
||||
base::ReadOnlySharedMemoryMapping shared_memory_;
|
||||
gfx::Size pixel_size_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(CefLayeredWindowUpdaterOSR);
|
||||
};
|
||||
|
||||
CefLayeredWindowUpdaterOSR::CefLayeredWindowUpdaterOSR(
|
||||
CefRenderWidgetHostViewOSR* const view,
|
||||
viz::mojom::LayeredWindowUpdaterRequest request)
|
||||
: view_(view), binding_(this, std::move(request)) {}
|
||||
|
||||
CefLayeredWindowUpdaterOSR::~CefLayeredWindowUpdaterOSR() = default;
|
||||
|
||||
void CefLayeredWindowUpdaterOSR::SetActive(bool active) {
|
||||
active_ = active;
|
||||
}
|
||||
|
||||
const void* CefLayeredWindowUpdaterOSR::GetPixelMemory() const {
|
||||
return shared_memory_.memory();
|
||||
}
|
||||
|
||||
gfx::Size CefLayeredWindowUpdaterOSR::GetPixelSize() const {
|
||||
return pixel_size_;
|
||||
}
|
||||
|
||||
void CefLayeredWindowUpdaterOSR::OnAllocatedSharedMemory(
|
||||
const gfx::Size& pixel_size,
|
||||
mojo::ScopedSharedBufferHandle scoped_buffer_handle) {
|
||||
// Make sure |pixel_size| is sane.
|
||||
size_t expected_bytes;
|
||||
bool size_result = viz::ResourceSizes::MaybeSizeInBytes(
|
||||
pixel_size, viz::ResourceFormat::RGBA_8888, &expected_bytes);
|
||||
if (!size_result)
|
||||
return;
|
||||
|
||||
#if !defined(OS_WIN)
|
||||
base::ReadOnlySharedMemoryRegion shm =
|
||||
mojo::UnwrapReadOnlySharedMemoryRegion(std::move(scoped_buffer_handle));
|
||||
if (!shm.IsValid()) {
|
||||
LOG(ERROR) << "Shared memory region is invalid";
|
||||
return;
|
||||
}
|
||||
#else // !defined(OS_WIN)
|
||||
base::SharedMemoryHandle shm_handle;
|
||||
MojoResult unwrap_result = mojo::UnwrapSharedMemoryHandle(
|
||||
std::move(scoped_buffer_handle), &shm_handle, nullptr, nullptr);
|
||||
if (unwrap_result != MOJO_RESULT_OK)
|
||||
return;
|
||||
|
||||
base::ReadOnlySharedMemoryRegion shm =
|
||||
base::ReadOnlySharedMemoryRegion::Deserialize(
|
||||
base::subtle::PlatformSharedMemoryRegion::TakeFromSharedMemoryHandle(
|
||||
shm_handle,
|
||||
base::subtle::PlatformSharedMemoryRegion::Mode::kReadOnly));
|
||||
#endif // !defined(OS_WIN)
|
||||
pixel_size_ = pixel_size;
|
||||
shared_memory_ = shm.Map();
|
||||
DCHECK(shared_memory_.IsValid());
|
||||
}
|
||||
|
||||
void CefLayeredWindowUpdaterOSR::Draw(const gfx::Rect& damage_rect,
|
||||
DrawCallback draw_callback) {
|
||||
if (active_) {
|
||||
const void* memory = GetPixelMemory();
|
||||
if (memory) {
|
||||
view_->OnPaint(damage_rect, pixel_size_, memory);
|
||||
} else {
|
||||
LOG(WARNING) << "Failed to read pixels";
|
||||
}
|
||||
}
|
||||
|
||||
std::move(draw_callback).Run();
|
||||
}
|
||||
|
||||
CefHostDisplayClientOSR::CefHostDisplayClientOSR(
|
||||
CefRenderWidgetHostViewOSR* const view,
|
||||
gfx::AcceleratedWidget widget)
|
||||
: viz::HostDisplayClient(widget), view_(view) {}
|
||||
|
||||
CefHostDisplayClientOSR::~CefHostDisplayClientOSR() {}
|
||||
|
||||
void CefHostDisplayClientOSR::SetActive(bool active) {
|
||||
active_ = active;
|
||||
if (layered_window_updater_) {
|
||||
layered_window_updater_->SetActive(active_);
|
||||
}
|
||||
}
|
||||
|
||||
const void* CefHostDisplayClientOSR::GetPixelMemory() const {
|
||||
return layered_window_updater_ ? layered_window_updater_->GetPixelMemory()
|
||||
: nullptr;
|
||||
}
|
||||
|
||||
gfx::Size CefHostDisplayClientOSR::GetPixelSize() const {
|
||||
return layered_window_updater_ ? layered_window_updater_->GetPixelSize()
|
||||
: gfx::Size{};
|
||||
}
|
||||
|
||||
void CefHostDisplayClientOSR::UseProxyOutputDevice(
|
||||
UseProxyOutputDeviceCallback callback) {
|
||||
std::move(callback).Run(true);
|
||||
}
|
||||
|
||||
void CefHostDisplayClientOSR::CreateLayeredWindowUpdater(
|
||||
viz::mojom::LayeredWindowUpdaterRequest request) {
|
||||
layered_window_updater_ =
|
||||
std::make_unique<CefLayeredWindowUpdaterOSR>(view_, std::move(request));
|
||||
layered_window_updater_->SetActive(active_);
|
||||
}
|
|
@ -0,0 +1,42 @@
|
|||
// Copyright 2019 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_OSR_HOST_DISPLAY_CLIENT_OSR_H_
|
||||
#define CEF_LIBCEF_BROWSER_OSR_HOST_DISPLAY_CLIENT_OSR_H_
|
||||
|
||||
#include <memory>
|
||||
|
||||
#include "base/callback.h"
|
||||
#include "base/memory/shared_memory.h"
|
||||
#include "components/viz/host/host_display_client.h"
|
||||
#include "ui/gfx/native_widget_types.h"
|
||||
|
||||
class CefLayeredWindowUpdaterOSR;
|
||||
class CefRenderWidgetHostViewOSR;
|
||||
|
||||
class CefHostDisplayClientOSR : public viz::HostDisplayClient {
|
||||
public:
|
||||
CefHostDisplayClientOSR(CefRenderWidgetHostViewOSR* const view,
|
||||
gfx::AcceleratedWidget widget);
|
||||
~CefHostDisplayClientOSR() override;
|
||||
|
||||
void SetActive(bool active);
|
||||
const void* GetPixelMemory() const;
|
||||
gfx::Size GetPixelSize() const;
|
||||
|
||||
private:
|
||||
// mojom::DisplayClient implementation.
|
||||
void UseProxyOutputDevice(UseProxyOutputDeviceCallback callback) override;
|
||||
|
||||
void CreateLayeredWindowUpdater(
|
||||
viz::mojom::LayeredWindowUpdaterRequest request) override;
|
||||
|
||||
CefRenderWidgetHostViewOSR* const view_;
|
||||
std::unique_ptr<CefLayeredWindowUpdaterOSR> layered_window_updater_;
|
||||
bool active_ = false;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(CefHostDisplayClientOSR);
|
||||
};
|
||||
|
||||
#endif // CEF_LIBCEF_BROWSER_OSR_HOST_DISPLAY_CLIENT_OSR_H_
|
|
@ -9,9 +9,10 @@
|
|||
|
||||
#include <utility>
|
||||
|
||||
#include "libcef/browser/browser_host_impl.h"
|
||||
#include "libcef/browser/osr/osr_util.h"
|
||||
#include "libcef/browser/osr/software_output_device_osr.h"
|
||||
#include "libcef/browser/osr/synthetic_gesture_target_osr.h"
|
||||
#include "libcef/browser/osr/video_consumer_osr.h"
|
||||
#include "libcef/browser/thread_util.h"
|
||||
|
||||
#include "base/callback_helpers.h"
|
||||
|
@ -61,9 +62,6 @@ const size_t kMaxDamageRects = 10;
|
|||
|
||||
const float kDefaultScaleFactor = 1.0;
|
||||
|
||||
// The maximum number of retry counts if frame capture fails.
|
||||
const int kFrameRetryLimit = 2;
|
||||
|
||||
static content::ScreenInfo ScreenInfoFrom(const CefScreenInfo& src) {
|
||||
content::ScreenInfo screenInfo;
|
||||
screenInfo.device_scale_factor = src.device_scale_factor;
|
||||
|
@ -79,43 +77,6 @@ static content::ScreenInfo ScreenInfoFrom(const CefScreenInfo& src) {
|
|||
return screenInfo;
|
||||
}
|
||||
|
||||
class CefCompositorFrameSinkClient
|
||||
: public viz::mojom::CompositorFrameSinkClient {
|
||||
public:
|
||||
CefCompositorFrameSinkClient(viz::mojom::CompositorFrameSinkClient* forward,
|
||||
CefRenderWidgetHostViewOSR* rwhv)
|
||||
: forward_(forward), render_widget_host_view_(rwhv) {}
|
||||
|
||||
void DidReceiveCompositorFrameAck(
|
||||
const std::vector<viz::ReturnedResource>& resources) override {
|
||||
forward_->DidReceiveCompositorFrameAck(resources);
|
||||
}
|
||||
|
||||
void OnBeginFrame(const viz::BeginFrameArgs& args,
|
||||
const base::flat_map<uint32_t, gfx::PresentationFeedback>&
|
||||
feedbacks) override {
|
||||
if (render_widget_host_view_) {
|
||||
render_widget_host_view_->OnPresentCompositorFrame();
|
||||
}
|
||||
forward_->OnBeginFrame(args, feedbacks);
|
||||
}
|
||||
|
||||
void OnBeginFramePausedChanged(bool paused) override {
|
||||
forward_->OnBeginFramePausedChanged(paused);
|
||||
}
|
||||
|
||||
void ReclaimResources(
|
||||
const std::vector<viz::ReturnedResource>& resources) override {
|
||||
forward_->ReclaimResources(resources);
|
||||
}
|
||||
|
||||
private:
|
||||
viz::mojom::CompositorFrameSinkClient* const forward_;
|
||||
CefRenderWidgetHostViewOSR* const render_widget_host_view_;
|
||||
};
|
||||
|
||||
#if !defined(OS_MACOSX)
|
||||
|
||||
class CefDelegatedFrameHostClient : public content::DelegatedFrameHostClient {
|
||||
public:
|
||||
explicit CefDelegatedFrameHostClient(CefRenderWidgetHostViewOSR* view)
|
||||
|
@ -169,8 +130,6 @@ class CefDelegatedFrameHostClient : public content::DelegatedFrameHostClient {
|
|||
DISALLOW_COPY_AND_ASSIGN(CefDelegatedFrameHostClient);
|
||||
};
|
||||
|
||||
#endif // !defined(OS_MACOSX)
|
||||
|
||||
ui::GestureProvider::Config CreateGestureProviderConfig() {
|
||||
ui::GestureProvider::Config config = ui::GetGestureProviderConfig(
|
||||
ui::GestureProviderConfigType::CURRENT_PLATFORM);
|
||||
|
@ -190,143 +149,6 @@ ui::LatencyInfo CreateLatencyInfo(const blink::WebInputEvent& event) {
|
|||
|
||||
} // namespace
|
||||
|
||||
// Used for managing copy requests when GPU compositing is enabled. Based on
|
||||
// RendererOverridesHandler::InnerSwapCompositorFrame and
|
||||
// DelegatedFrameHost::CopyFromCompositingSurface.
|
||||
class CefCopyFrameGenerator {
|
||||
public:
|
||||
CefCopyFrameGenerator(int frame_rate_threshold_us,
|
||||
CefRenderWidgetHostViewOSR* view)
|
||||
: view_(view),
|
||||
frame_retry_count_(0),
|
||||
next_frame_time_(base::TimeTicks::Now()),
|
||||
frame_duration_(
|
||||
base::TimeDelta::FromMicroseconds(frame_rate_threshold_us)),
|
||||
weak_ptr_factory_(this) {}
|
||||
|
||||
void GenerateCopyFrame(const gfx::Rect& damage_rect) {
|
||||
if (!view_->render_widget_host())
|
||||
return;
|
||||
// The below code is similar in functionality to
|
||||
// DelegatedFrameHost::CopyFromCompositingSurface but we reuse the same
|
||||
// SkBitmap in the GPU codepath and avoid scaling where possible.
|
||||
// Let the compositor copy into a new SkBitmap
|
||||
std::unique_ptr<viz::CopyOutputRequest> request =
|
||||
std::make_unique<viz::CopyOutputRequest>(
|
||||
viz::CopyOutputRequest::ResultFormat::RGBA_BITMAP,
|
||||
base::Bind(
|
||||
&CefCopyFrameGenerator::CopyFromCompositingSurfaceHasResult,
|
||||
weak_ptr_factory_.GetWeakPtr(), damage_rect));
|
||||
|
||||
request->set_area(gfx::Rect(view_->GetCompositorViewportPixelSize()));
|
||||
view_->GetRootLayer()->RequestCopyOfOutput(std::move(request));
|
||||
}
|
||||
|
||||
void set_frame_rate_threshold_us(int frame_rate_threshold_us) {
|
||||
frame_duration_ =
|
||||
base::TimeDelta::FromMicroseconds(frame_rate_threshold_us);
|
||||
}
|
||||
|
||||
private:
|
||||
void CopyFromCompositingSurfaceHasResult(
|
||||
const gfx::Rect& damage_rect,
|
||||
std::unique_ptr<viz::CopyOutputResult> result) {
|
||||
if (result->IsEmpty() || result->size().IsEmpty() ||
|
||||
!view_->render_widget_host()) {
|
||||
OnCopyFrameCaptureFailure(damage_rect);
|
||||
return;
|
||||
}
|
||||
|
||||
std::unique_ptr<SkBitmap> source =
|
||||
std::make_unique<SkBitmap>(result->AsSkBitmap());
|
||||
DCHECK(source);
|
||||
|
||||
if (source) {
|
||||
std::shared_ptr<SkBitmap> bitmap(std::move(source));
|
||||
|
||||
base::TimeTicks now = base::TimeTicks::Now();
|
||||
base::TimeDelta next_frame_in = next_frame_time_ - now;
|
||||
if (next_frame_in > frame_duration_ / 4) {
|
||||
next_frame_time_ += frame_duration_;
|
||||
base::PostDelayedTaskWithTraits(
|
||||
FROM_HERE, {content::BrowserThread::UI},
|
||||
base::Bind(&CefCopyFrameGenerator::OnCopyFrameCaptureSuccess,
|
||||
weak_ptr_factory_.GetWeakPtr(), damage_rect, bitmap),
|
||||
next_frame_in);
|
||||
} else {
|
||||
next_frame_time_ = now + frame_duration_;
|
||||
OnCopyFrameCaptureSuccess(damage_rect, bitmap);
|
||||
}
|
||||
|
||||
// Reset the frame retry count on successful frame generation.
|
||||
frame_retry_count_ = 0;
|
||||
} else {
|
||||
OnCopyFrameCaptureFailure(damage_rect);
|
||||
}
|
||||
}
|
||||
|
||||
void OnCopyFrameCaptureFailure(const gfx::Rect& damage_rect) {
|
||||
const bool force_frame = (++frame_retry_count_ <= kFrameRetryLimit);
|
||||
if (force_frame) {
|
||||
// Retry with the same |damage_rect|.
|
||||
CEF_POST_TASK(CEF_UIT,
|
||||
base::Bind(&CefCopyFrameGenerator::GenerateCopyFrame,
|
||||
weak_ptr_factory_.GetWeakPtr(), damage_rect));
|
||||
}
|
||||
}
|
||||
|
||||
void OnCopyFrameCaptureSuccess(const gfx::Rect& damage_rect,
|
||||
std::shared_ptr<SkBitmap> bitmap) {
|
||||
view_->OnPaint(damage_rect, bitmap->width(), bitmap->height(),
|
||||
bitmap->getPixels());
|
||||
}
|
||||
|
||||
CefRenderWidgetHostViewOSR* const view_;
|
||||
int frame_retry_count_;
|
||||
base::TimeTicks next_frame_time_;
|
||||
base::TimeDelta frame_duration_;
|
||||
|
||||
base::WeakPtrFactory<CefCopyFrameGenerator> weak_ptr_factory_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(CefCopyFrameGenerator);
|
||||
};
|
||||
|
||||
// Used to control the VSync rate in subprocesses when BeginFrame scheduling is
|
||||
// enabled.
|
||||
class CefBeginFrameTimer : public viz::DelayBasedTimeSourceClient {
|
||||
public:
|
||||
CefBeginFrameTimer(int frame_rate_threshold_us, const base::Closure& callback)
|
||||
: callback_(callback) {
|
||||
time_source_.reset(new viz::DelayBasedTimeSource(
|
||||
base::CreateSingleThreadTaskRunnerWithTraits(
|
||||
{content::BrowserThread::UI})
|
||||
.get()));
|
||||
time_source_->SetTimebaseAndInterval(
|
||||
base::TimeTicks(),
|
||||
base::TimeDelta::FromMicroseconds(frame_rate_threshold_us));
|
||||
time_source_->SetClient(this);
|
||||
}
|
||||
|
||||
void SetActive(bool active) { time_source_->SetActive(active); }
|
||||
|
||||
bool IsActive() const { return time_source_->Active(); }
|
||||
|
||||
void SetFrameRateThresholdUs(int frame_rate_threshold_us) {
|
||||
time_source_->SetTimebaseAndInterval(
|
||||
base::TimeTicks::Now(),
|
||||
base::TimeDelta::FromMicroseconds(frame_rate_threshold_us));
|
||||
}
|
||||
|
||||
private:
|
||||
// cc::TimerSourceClient implementation.
|
||||
void OnTimerTick() override { callback_.Run(); }
|
||||
|
||||
const base::Closure callback_;
|
||||
std::unique_ptr<viz::DelayBasedTimeSource> time_source_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(CefBeginFrameTimer);
|
||||
};
|
||||
|
||||
CefRenderWidgetHostViewOSR::CefRenderWidgetHostViewOSR(
|
||||
SkColor background_color,
|
||||
bool use_shared_texture,
|
||||
|
@ -337,10 +159,6 @@ CefRenderWidgetHostViewOSR::CefRenderWidgetHostViewOSR(
|
|||
: content::RenderWidgetHostViewBase(widget),
|
||||
background_color_(background_color),
|
||||
frame_rate_threshold_us_(0),
|
||||
#if !defined(OS_MACOSX)
|
||||
compositor_widget_(gfx::kNullAcceleratedWidget),
|
||||
#endif
|
||||
software_output_device_(NULL),
|
||||
hold_resize_(false),
|
||||
pending_resize_(false),
|
||||
pending_resize_force_(false),
|
||||
|
@ -349,7 +167,7 @@ CefRenderWidgetHostViewOSR::CefRenderWidgetHostViewOSR(
|
|||
parent_host_view_(parent_host_view),
|
||||
popup_host_view_(NULL),
|
||||
child_host_view_(NULL),
|
||||
is_showing_(!render_widget_host_->is_hidden()),
|
||||
is_showing_(false),
|
||||
is_destroyed_(false),
|
||||
pinch_zoom_enabled_(content::IsPinchToZoomEnabled()),
|
||||
is_scroll_offset_changed_pending_(false),
|
||||
|
@ -371,7 +189,6 @@ CefRenderWidgetHostViewOSR::CefRenderWidgetHostViewOSR(
|
|||
content::RenderViewHost::From(render_widget_host_));
|
||||
}
|
||||
|
||||
#if !defined(OS_MACOSX)
|
||||
local_surface_id_allocator_.GenerateId();
|
||||
local_surface_id_allocation_ =
|
||||
local_surface_id_allocator_.GetCurrentLocalSurfaceIdAllocation();
|
||||
|
@ -384,9 +201,6 @@ CefRenderWidgetHostViewOSR::CefRenderWidgetHostViewOSR(
|
|||
false /* should_register_frame_sink_id */);
|
||||
|
||||
root_layer_.reset(new ui::Layer(ui::LAYER_SOLID_COLOR));
|
||||
#endif
|
||||
|
||||
PlatformCreateCompositorWidget(is_guest_view_hack);
|
||||
|
||||
bool opaque = SkColorGetA(background_color_) == SK_AlphaOPAQUE;
|
||||
GetRootLayer()->SetFillsBoundsOpaquely(opaque);
|
||||
|
@ -394,28 +208,22 @@ CefRenderWidgetHostViewOSR::CefRenderWidgetHostViewOSR(
|
|||
|
||||
external_begin_frame_enabled_ = use_external_begin_frame;
|
||||
|
||||
#if !defined(OS_MACOSX)
|
||||
// On macOS the ui::Compositor is created/owned by the platform view.
|
||||
content::ImageTransportFactory* factory =
|
||||
content::ImageTransportFactory::GetInstance();
|
||||
ui::ContextFactoryPrivate* context_factory_private =
|
||||
factory->GetContextFactoryPrivate();
|
||||
|
||||
// Matching the attributes from RecyclableCompositorMac.
|
||||
compositor_.reset(new ui::Compositor(
|
||||
context_factory_private->AllocateFrameSinkId(),
|
||||
content::GetContextFactory(), context_factory_private,
|
||||
base::ThreadTaskRunnerHandle::Get(), false /* enable_pixel_canvas */,
|
||||
use_external_begin_frame ? this : nullptr));
|
||||
compositor_->SetAcceleratedWidget(compositor_widget_);
|
||||
|
||||
// Tell the compositor to use shared textures if the client can handle
|
||||
// OnAcceleratedPaint.
|
||||
compositor_->EnableSharedTexture(use_shared_texture);
|
||||
compositor_->SetAcceleratedWidget(gfx::kNullAcceleratedWidget);
|
||||
|
||||
compositor_->SetDelegate(this);
|
||||
compositor_->SetRootLayer(root_layer_.get());
|
||||
compositor_->AddChildFrameSink(GetFrameSinkId());
|
||||
#endif
|
||||
|
||||
if (browser_impl_.get())
|
||||
ResizeRootLayer(false);
|
||||
|
@ -433,34 +241,33 @@ CefRenderWidgetHostViewOSR::CefRenderWidgetHostViewOSR(
|
|||
render_widget_host_->delegate()->GetInputEventRouter()->AddFrameSinkIdOwner(
|
||||
GetFrameSinkId(), this);
|
||||
}
|
||||
|
||||
if (!render_widget_host_->is_hidden()) {
|
||||
Show();
|
||||
}
|
||||
|
||||
if (!factory->IsGpuCompositingDisabled()) {
|
||||
video_consumer_.reset(new CefVideoConsumerOSR(this));
|
||||
video_consumer_->SetActive(true);
|
||||
video_consumer_->SetFrameRate(
|
||||
base::TimeDelta::FromMicroseconds(frame_rate_threshold_us_));
|
||||
}
|
||||
}
|
||||
|
||||
CefRenderWidgetHostViewOSR::~CefRenderWidgetHostViewOSR() {
|
||||
#if defined(OS_MACOSX)
|
||||
if (is_showing_)
|
||||
browser_compositor_->SetRenderWidgetHostIsHidden(true);
|
||||
#else
|
||||
// Marking the DelegatedFrameHost as removed from the window hierarchy is
|
||||
// necessary to remove all connections to its old ui::Compositor.
|
||||
if (is_showing_)
|
||||
delegated_frame_host_->WasHidden();
|
||||
delegated_frame_host_->DetachFromCompositor();
|
||||
#endif
|
||||
|
||||
PlatformDestroyCompositorWidget();
|
||||
delegated_frame_host_.reset(nullptr);
|
||||
compositor_.reset(nullptr);
|
||||
root_layer_.reset(nullptr);
|
||||
|
||||
if (copy_frame_generator_.get())
|
||||
copy_frame_generator_.reset(NULL);
|
||||
|
||||
#if !defined(OS_MACOSX)
|
||||
delegated_frame_host_.reset(NULL);
|
||||
compositor_.reset(NULL);
|
||||
root_layer_.reset(NULL);
|
||||
#endif
|
||||
|
||||
DCHECK(parent_host_view_ == NULL);
|
||||
DCHECK(popup_host_view_ == NULL);
|
||||
DCHECK(child_host_view_ == NULL);
|
||||
DCHECK(!parent_host_view_);
|
||||
DCHECK(!popup_host_view_);
|
||||
DCHECK(!child_host_view_);
|
||||
DCHECK(guest_host_views_.empty());
|
||||
|
||||
if (text_input_manager_)
|
||||
|
@ -515,14 +322,10 @@ void CefRenderWidgetHostViewOSR::Show() {
|
|||
|
||||
is_showing_ = true;
|
||||
|
||||
#if defined(OS_MACOSX)
|
||||
browser_compositor_->SetRenderWidgetHostIsHidden(false);
|
||||
#else
|
||||
delegated_frame_host_->AttachToCompositor(compositor_.get());
|
||||
delegated_frame_host_->WasShown(
|
||||
GetLocalSurfaceIdAllocation().local_surface_id(),
|
||||
GetRootLayer()->bounds().size(), base::nullopt);
|
||||
#endif
|
||||
|
||||
// Note that |render_widget_host_| will retrieve size parameters from the
|
||||
// DelegatedFrameHost, so it must have WasShown called after.
|
||||
|
@ -543,12 +346,8 @@ void CefRenderWidgetHostViewOSR::Hide() {
|
|||
if (render_widget_host_)
|
||||
render_widget_host_->WasHidden();
|
||||
|
||||
#if defined(OS_MACOSX)
|
||||
browser_compositor_->SetRenderWidgetHostIsHidden(true);
|
||||
#else
|
||||
GetDelegatedFrameHost()->WasHidden();
|
||||
GetDelegatedFrameHost()->DetachFromCompositor();
|
||||
#endif
|
||||
}
|
||||
|
||||
bool CefRenderWidgetHostViewOSR::IsShowing() {
|
||||
|
@ -619,53 +418,10 @@ void CefRenderWidgetHostViewOSR::TakeFallbackContentFrom(
|
|||
|
||||
void CefRenderWidgetHostViewOSR::DidCreateNewRendererCompositorFrameSink(
|
||||
viz::mojom::CompositorFrameSinkClient* renderer_compositor_frame_sink) {
|
||||
renderer_compositor_frame_sink_.reset(
|
||||
new CefCompositorFrameSinkClient(renderer_compositor_frame_sink, this));
|
||||
if (GetDelegatedFrameHost()) {
|
||||
GetDelegatedFrameHost()->DidCreateNewRendererCompositorFrameSink(
|
||||
renderer_compositor_frame_sink_.get());
|
||||
}
|
||||
NOTREACHED();
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::OnPresentCompositorFrame() {
|
||||
// Is Chromium rendering to a shared texture?
|
||||
void* shared_texture = nullptr;
|
||||
ui::Compositor* compositor = GetCompositor();
|
||||
if (compositor) {
|
||||
shared_texture = compositor->GetSharedTexture();
|
||||
}
|
||||
|
||||
if (shared_texture) {
|
||||
CefRefPtr<CefRenderHandler> handler =
|
||||
browser_impl_->GetClient()->GetRenderHandler();
|
||||
CHECK(handler);
|
||||
|
||||
CefRenderHandler::RectList rcList;
|
||||
|
||||
{
|
||||
// Find the corresponding damage rect. If there isn't one pass the entire
|
||||
// view size for a full redraw.
|
||||
base::AutoLock lock_scope(damage_rect_lock_);
|
||||
|
||||
// TODO: in the future we need to correlate the presentation
|
||||
// notification with the sequence number from BeginFrame
|
||||
gfx::Rect damage;
|
||||
auto const i = damage_rects_.begin();
|
||||
if (i != damage_rects_.end()) {
|
||||
damage = i->second;
|
||||
damage_rects_.erase(i);
|
||||
} else {
|
||||
damage = GetViewBounds();
|
||||
}
|
||||
rcList.push_back(
|
||||
CefRect(damage.x(), damage.y(), damage.width(), damage.height()));
|
||||
}
|
||||
|
||||
handler->OnAcceleratedPaint(browser_impl_.get(),
|
||||
IsPopupWidget() ? PET_POPUP : PET_VIEW, rcList,
|
||||
shared_texture);
|
||||
}
|
||||
}
|
||||
void CefRenderWidgetHostViewOSR::OnPresentCompositorFrame() {}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::AddDamageRect(uint32_t sequence,
|
||||
const gfx::Rect& rect) {
|
||||
|
@ -687,93 +443,10 @@ void CefRenderWidgetHostViewOSR::SubmitCompositorFrame(
|
|||
const viz::LocalSurfaceId& local_surface_id,
|
||||
viz::CompositorFrame frame,
|
||||
base::Optional<viz::HitTestRegionList> hit_test_region_list) {
|
||||
TRACE_EVENT0("cef", "CefRenderWidgetHostViewOSR::OnSwapCompositorFrame");
|
||||
|
||||
// Update the frame rate. At this point we should have a valid connection back
|
||||
// to the Synthetic Frame Source, which is important so we can actually modify
|
||||
// the frame rate to something other than the default of 60Hz.
|
||||
if (sync_frame_rate_) {
|
||||
if (frame_rate_threshold_us_ != 0) {
|
||||
GetCompositor()->SetDisplayVSyncParameters(
|
||||
base::TimeTicks::Now(),
|
||||
base::TimeDelta::FromMicroseconds(frame_rate_threshold_us_));
|
||||
}
|
||||
sync_frame_rate_ = false;
|
||||
}
|
||||
|
||||
if (frame.metadata.root_scroll_offset != last_scroll_offset_) {
|
||||
last_scroll_offset_ = frame.metadata.root_scroll_offset;
|
||||
|
||||
if (!is_scroll_offset_changed_pending_) {
|
||||
// Send the notification asnychronously.
|
||||
CEF_POST_TASK(
|
||||
CEF_UIT,
|
||||
base::Bind(&CefRenderWidgetHostViewOSR::OnScrollOffsetChanged,
|
||||
weak_ptr_factory_.GetWeakPtr()));
|
||||
}
|
||||
}
|
||||
|
||||
if (!frame.render_pass_list.empty()) {
|
||||
if (software_output_device_) {
|
||||
if (!begin_frame_timer_.get()) {
|
||||
// If BeginFrame scheduling is enabled SoftwareOutputDevice activity
|
||||
// will be controlled via OnSetNeedsBeginFrames. Otherwise, activate
|
||||
// the SoftwareOutputDevice now (when the first frame is generated).
|
||||
software_output_device_->SetActive(true);
|
||||
}
|
||||
|
||||
// The compositor will draw directly to the SoftwareOutputDevice which
|
||||
// then calls OnPaint.
|
||||
// We would normally call BrowserCompositorMac::SubmitCompositorFrame on
|
||||
// macOS, however it contains compositor resize logic that we don't want.
|
||||
// Consequently we instead call the SwapDelegatedFrame method directly.
|
||||
GetDelegatedFrameHost()->SubmitCompositorFrame(
|
||||
local_surface_id, std::move(frame), std::move(hit_test_region_list));
|
||||
} else {
|
||||
ui::Compositor* compositor = GetCompositor();
|
||||
if (!compositor)
|
||||
return;
|
||||
|
||||
// Will be nullptr if we're not using shared textures.
|
||||
const void* shared_texture = compositor->GetSharedTexture();
|
||||
|
||||
// Determine the damage rectangle for the current frame. This is the
|
||||
// same calculation that SwapDelegatedFrame uses.
|
||||
viz::RenderPass* root_pass = frame.render_pass_list.back().get();
|
||||
gfx::Size frame_size = root_pass->output_rect.size();
|
||||
gfx::Rect damage_rect =
|
||||
gfx::ToEnclosingRect(gfx::RectF(root_pass->damage_rect));
|
||||
damage_rect.Intersect(gfx::Rect(frame_size));
|
||||
|
||||
if (shared_texture) {
|
||||
AddDamageRect(frame.metadata.begin_frame_ack.sequence_number,
|
||||
damage_rect);
|
||||
}
|
||||
|
||||
// We would normally call BrowserCompositorMac::SubmitCompositorFrame on
|
||||
// macOS, however it contains compositor resize logic that we don't
|
||||
// want. Consequently we instead call the SwapDelegatedFrame method
|
||||
// directly.
|
||||
GetDelegatedFrameHost()->SubmitCompositorFrame(
|
||||
local_surface_id, std::move(frame), std::move(hit_test_region_list));
|
||||
|
||||
if (!shared_texture) {
|
||||
if (!copy_frame_generator_.get()) {
|
||||
copy_frame_generator_.reset(
|
||||
new CefCopyFrameGenerator(frame_rate_threshold_us_, this));
|
||||
}
|
||||
|
||||
// Request a copy of the last compositor frame which will eventually
|
||||
// call OnPaint asynchronously.
|
||||
copy_frame_generator_->GenerateCopyFrame(damage_rect);
|
||||
}
|
||||
}
|
||||
}
|
||||
NOTREACHED();
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::ClearCompositorFrame() {
|
||||
// This method is only used for content rendering timeout when surface sync is
|
||||
// off.
|
||||
NOTREACHED();
|
||||
}
|
||||
|
||||
|
@ -806,7 +479,12 @@ void CefRenderWidgetHostViewOSR::InitAsPopup(
|
|||
if (handler.get())
|
||||
handler->OnPopupSize(browser_impl_.get(), widget_pos);
|
||||
|
||||
if (video_consumer_) {
|
||||
video_consumer_->SizeChanged();
|
||||
}
|
||||
|
||||
ResizeRootLayer(false);
|
||||
|
||||
Show();
|
||||
}
|
||||
|
||||
|
@ -1113,23 +791,17 @@ void CefRenderWidgetHostViewOSR::SelectionChanged(const base::string16& text,
|
|||
cef_range);
|
||||
}
|
||||
|
||||
#if !defined(OS_MACOSX)
|
||||
const viz::LocalSurfaceIdAllocation&
|
||||
CefRenderWidgetHostViewOSR::GetLocalSurfaceIdAllocation() const {
|
||||
return local_surface_id_allocation_;
|
||||
}
|
||||
#endif
|
||||
|
||||
const viz::FrameSinkId& CefRenderWidgetHostViewOSR::GetFrameSinkId() const {
|
||||
return GetDelegatedFrameHost()->frame_sink_id();
|
||||
}
|
||||
|
||||
viz::FrameSinkId CefRenderWidgetHostViewOSR::GetRootFrameSinkId() {
|
||||
#if defined(OS_MACOSX)
|
||||
return browser_compositor_->GetRootFrameSinkId();
|
||||
#else
|
||||
return compositor_->frame_sink_id();
|
||||
#endif
|
||||
}
|
||||
|
||||
std::unique_ptr<content::SyntheticGestureTarget>
|
||||
|
@ -1137,33 +809,10 @@ CefRenderWidgetHostViewOSR::CreateSyntheticGestureTarget() {
|
|||
return std::make_unique<CefSyntheticGestureTargetOSR>(host());
|
||||
}
|
||||
|
||||
#if !defined(OS_MACOSX)
|
||||
viz::ScopedSurfaceIdAllocator
|
||||
CefRenderWidgetHostViewOSR::DidUpdateVisualProperties(
|
||||
const cc::RenderFrameMetadata& metadata) {
|
||||
bool force =
|
||||
local_surface_id_allocation_ != metadata.local_surface_id_allocation;
|
||||
base::OnceCallback<void()> allocation_task =
|
||||
base::BindOnce(&CefRenderWidgetHostViewOSR::SynchronizeVisualProperties,
|
||||
weak_ptr_factory_.GetWeakPtr(), force);
|
||||
return viz::ScopedSurfaceIdAllocator(std::move(allocation_task));
|
||||
}
|
||||
#endif
|
||||
|
||||
void CefRenderWidgetHostViewOSR::SetNeedsBeginFrames(bool enabled) {
|
||||
SetFrameRate();
|
||||
|
||||
if (!external_begin_frame_enabled_) {
|
||||
// Start/stop the timer that sends BeginFrame requests.
|
||||
begin_frame_timer_->SetActive(enabled);
|
||||
}
|
||||
|
||||
if (software_output_device_) {
|
||||
// When the SoftwareOutputDevice is active it will call OnPaint for each
|
||||
// frame. If the SoftwareOutputDevice is deactivated while an invalidation
|
||||
// region is pending it will call OnPaint immediately.
|
||||
software_output_device_->SetActive(enabled);
|
||||
}
|
||||
host_display_client_->SetActive(enabled);
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::SetWantsAnimateOnlyBeginFrames() {
|
||||
|
@ -1206,12 +855,8 @@ void CefRenderWidgetHostViewOSR::DidNavigate() {
|
|||
// With surface synchronization enabled we need to force synchronization on
|
||||
// first navigation.
|
||||
ResizeRootLayer(true);
|
||||
#if defined(OS_MACOSX)
|
||||
browser_compositor_->DidNavigate();
|
||||
#else
|
||||
if (delegated_frame_host_)
|
||||
delegated_frame_host_->DidNavigate();
|
||||
#endif
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::OnDisplayDidFinishFrame(
|
||||
|
@ -1221,30 +866,24 @@ void CefRenderWidgetHostViewOSR::OnDisplayDidFinishFrame(
|
|||
|
||||
void CefRenderWidgetHostViewOSR::OnNeedsExternalBeginFrames(
|
||||
bool needs_begin_frames) {
|
||||
SetFrameRate();
|
||||
needs_external_begin_frames_ = needs_begin_frames;
|
||||
}
|
||||
|
||||
std::unique_ptr<viz::SoftwareOutputDevice>
|
||||
CefRenderWidgetHostViewOSR::CreateSoftwareOutputDevice(
|
||||
ui::Compositor* compositor) {
|
||||
DCHECK_EQ(GetCompositor(), compositor);
|
||||
DCHECK(!copy_frame_generator_);
|
||||
DCHECK(!software_output_device_);
|
||||
software_output_device_ = new CefSoftwareOutputDeviceOSR(
|
||||
compositor, background_color_ == SK_ColorTRANSPARENT,
|
||||
base::Bind(&CefRenderWidgetHostViewOSR::OnPaint,
|
||||
weak_ptr_factory_.GetWeakPtr()));
|
||||
return base::WrapUnique(software_output_device_);
|
||||
std::unique_ptr<viz::HostDisplayClient>
|
||||
CefRenderWidgetHostViewOSR::CreateHostDisplayClient() {
|
||||
host_display_client_ =
|
||||
new CefHostDisplayClientOSR(this, gfx::kNullAcceleratedWidget);
|
||||
host_display_client_->SetActive(true);
|
||||
return base::WrapUnique(host_display_client_);
|
||||
}
|
||||
|
||||
bool CefRenderWidgetHostViewOSR::InstallTransparency() {
|
||||
if (background_color_ == SK_ColorTRANSPARENT) {
|
||||
SetBackgroundColor(background_color_);
|
||||
#if defined(OS_MACOSX)
|
||||
browser_compositor_->SetBackgroundColor(background_color_);
|
||||
#else
|
||||
compositor_->SetBackgroundColor(background_color_);
|
||||
#endif
|
||||
if (compositor_) {
|
||||
compositor_->SetBackgroundColor(background_color_);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
|
@ -1274,16 +913,7 @@ void CefRenderWidgetHostViewOSR::OnScreenInfoChanged() {
|
|||
else
|
||||
render_widget_host_->SendScreenRects();
|
||||
|
||||
#if defined(OS_MACOSX)
|
||||
// RenderWidgetHostImpl will query BrowserCompositorMac for the dimensions
|
||||
// to send to the renderer, so it is required that BrowserCompositorMac be
|
||||
// updated first. Only notify RenderWidgetHostImpl of the update if any
|
||||
// properties it will query have changed.
|
||||
if (UpdateNSViewAndDisplay())
|
||||
render_widget_host_->NotifyScreenInfoChanged();
|
||||
#else
|
||||
render_widget_host_->NotifyScreenInfoChanged();
|
||||
#endif
|
||||
|
||||
// We might want to change the cursor scale factor here as well - see the
|
||||
// cache for the current_cursor_, as passed by UpdateCursor from the
|
||||
|
@ -1302,8 +932,7 @@ void CefRenderWidgetHostViewOSR::Invalidate(
|
|||
popup_host_view_->Invalidate(type);
|
||||
return;
|
||||
}
|
||||
|
||||
InvalidateInternal(gfx::Rect(GetCompositorViewportPixelSize()));
|
||||
InvalidateInternal(gfx::Rect(SizeInPixels()));
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::SendExternalBeginFrame() {
|
||||
|
@ -1324,11 +953,8 @@ void CefRenderWidgetHostViewOSR::SendExternalBeginFrame() {
|
|||
if (render_widget_host_)
|
||||
render_widget_host_->ProgressFlingIfNeeded(frame_time);
|
||||
|
||||
if (renderer_compositor_frame_sink_) {
|
||||
GetCompositor()->context_factory_private()->IssueExternalBeginFrame(
|
||||
GetCompositor(), begin_frame_args);
|
||||
renderer_compositor_frame_sink_->OnBeginFrame(begin_frame_args, {});
|
||||
}
|
||||
GetCompositor()->context_factory_private()->IssueExternalBeginFrame(
|
||||
GetCompositor(), begin_frame_args);
|
||||
|
||||
if (!IsPopupWidget() && popup_host_view_) {
|
||||
popup_host_view_->SendExternalBeginFrame();
|
||||
|
@ -1653,12 +1279,28 @@ void CefRenderWidgetHostViewOSR::ReleaseResize() {
|
|||
}
|
||||
}
|
||||
|
||||
gfx::Size CefRenderWidgetHostViewOSR::SizeInPixels() {
|
||||
return gfx::ConvertSizeToPixel(current_device_scale_factor_,
|
||||
GetViewBounds().size());
|
||||
}
|
||||
|
||||
#if defined(OS_MACOSX)
|
||||
void CefRenderWidgetHostViewOSR::SetActive(bool active) {}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::ShowDefinitionForSelection() {}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::SpeakSelection() {}
|
||||
#endif
|
||||
|
||||
void CefRenderWidgetHostViewOSR::OnPaint(const gfx::Rect& damage_rect,
|
||||
int bitmap_width,
|
||||
int bitmap_height,
|
||||
void* bitmap_pixels) {
|
||||
const gfx::Size& pixel_size,
|
||||
const void* pixels) {
|
||||
TRACE_EVENT0("cef", "CefRenderWidgetHostViewOSR::OnPaint");
|
||||
|
||||
if (!pixels) {
|
||||
return;
|
||||
}
|
||||
|
||||
CefRefPtr<CefRenderHandler> handler =
|
||||
browser_impl_->client()->GetRenderHandler();
|
||||
CHECK(handler);
|
||||
|
@ -1667,21 +1309,19 @@ void CefRenderWidgetHostViewOSR::OnPaint(const gfx::Rect& damage_rect,
|
|||
// pending.
|
||||
HoldResize();
|
||||
|
||||
gfx::Rect rect_in_bitmap(0, 0, bitmap_width, bitmap_height);
|
||||
rect_in_bitmap.Intersect(damage_rect);
|
||||
gfx::Rect rect_in_pixels(0, 0, pixel_size.width(), pixel_size.height());
|
||||
rect_in_pixels.Intersect(damage_rect);
|
||||
|
||||
CefRenderHandler::RectList rcList;
|
||||
rcList.push_back(CefRect(rect_in_bitmap.x(), rect_in_bitmap.y(),
|
||||
rect_in_bitmap.width(), rect_in_bitmap.height()));
|
||||
rcList.push_back(CefRect(rect_in_pixels.x(), rect_in_pixels.y(),
|
||||
rect_in_pixels.width(), rect_in_pixels.height()));
|
||||
|
||||
handler->OnPaint(browser_impl_.get(), IsPopupWidget() ? PET_POPUP : PET_VIEW,
|
||||
rcList, bitmap_pixels, bitmap_width, bitmap_height);
|
||||
rcList, pixels, pixel_size.width(), pixel_size.height());
|
||||
|
||||
ReleaseResize();
|
||||
}
|
||||
|
||||
#if !defined(OS_MACOSX)
|
||||
|
||||
ui::Compositor* CefRenderWidgetHostViewOSR::GetCompositor() const {
|
||||
return compositor_.get();
|
||||
}
|
||||
|
@ -1695,8 +1335,6 @@ content::DelegatedFrameHost* CefRenderWidgetHostViewOSR::GetDelegatedFrameHost()
|
|||
return delegated_frame_host_.get();
|
||||
}
|
||||
|
||||
#endif // !defined(OS_MACOSX)
|
||||
|
||||
void CefRenderWidgetHostViewOSR::SetFrameRate() {
|
||||
CefRefPtr<CefBrowserHostImpl> browser;
|
||||
if (parent_host_view_) {
|
||||
|
@ -1713,18 +1351,8 @@ void CefRenderWidgetHostViewOSR::SetFrameRate() {
|
|||
|
||||
ui::Compositor* compositor = GetCompositor();
|
||||
|
||||
int frame_rate;
|
||||
if (compositor && compositor->shared_texture_enabled()) {
|
||||
// No upper-bound when using OnAcceleratedPaint.
|
||||
frame_rate = browser->settings().windowless_frame_rate;
|
||||
if (frame_rate <= 0) {
|
||||
frame_rate = 1;
|
||||
}
|
||||
sync_frame_rate_ = true;
|
||||
} else {
|
||||
frame_rate =
|
||||
osr_util::ClampFrameRate(browser->settings().windowless_frame_rate);
|
||||
}
|
||||
int frame_rate =
|
||||
osr_util::ClampFrameRate(browser->settings().windowless_frame_rate);
|
||||
|
||||
frame_rate_threshold_us_ = 1000000 / frame_rate;
|
||||
|
||||
|
@ -1742,20 +1370,9 @@ void CefRenderWidgetHostViewOSR::SetFrameRate() {
|
|||
}
|
||||
#endif
|
||||
|
||||
if (copy_frame_generator_.get()) {
|
||||
copy_frame_generator_->set_frame_rate_threshold_us(
|
||||
frame_rate_threshold_us_);
|
||||
}
|
||||
|
||||
if (!external_begin_frame_enabled_) {
|
||||
if (begin_frame_timer_.get()) {
|
||||
begin_frame_timer_->SetFrameRateThresholdUs(frame_rate_threshold_us_);
|
||||
} else {
|
||||
begin_frame_timer_.reset(new CefBeginFrameTimer(
|
||||
frame_rate_threshold_us_,
|
||||
base::Bind(&CefRenderWidgetHostViewOSR::OnBeginFrameTimerTick,
|
||||
weak_ptr_factory_.GetWeakPtr())));
|
||||
}
|
||||
if (video_consumer_) {
|
||||
video_consumer_->SetFrameRate(
|
||||
base::TimeDelta::FromMicroseconds(frame_rate_threshold_us_));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1806,9 +1423,6 @@ void CefRenderWidgetHostViewOSR::ResizeRootLayer(bool force) {
|
|||
|
||||
GetRootLayer()->SetBounds(gfx::Rect(size));
|
||||
|
||||
#if defined(OS_MACOSX)
|
||||
bool resized = UpdateNSViewAndDisplay();
|
||||
#else
|
||||
const gfx::Size& size_in_pixels =
|
||||
gfx::ConvertSizeToPixel(current_device_scale_factor_, size);
|
||||
|
||||
|
@ -1817,59 +1431,22 @@ void CefRenderWidgetHostViewOSR::ResizeRootLayer(bool force) {
|
|||
local_surface_id_allocator_.GetCurrentLocalSurfaceIdAllocation();
|
||||
|
||||
if (GetCompositor()) {
|
||||
compositor_local_surface_id_allocator_.GenerateId();
|
||||
GetCompositor()->SetScaleAndSize(current_device_scale_factor_,
|
||||
size_in_pixels,
|
||||
local_surface_id_allocation_);
|
||||
compositor_local_surface_id_allocator_
|
||||
.GetCurrentLocalSurfaceIdAllocation());
|
||||
}
|
||||
PlatformResizeCompositorWidget(size_in_pixels);
|
||||
|
||||
bool resized = true;
|
||||
GetDelegatedFrameHost()->EmbedSurface(
|
||||
local_surface_id_allocation_.local_surface_id(), size,
|
||||
cc::DeadlinePolicy::UseDefaultDeadline());
|
||||
#endif // !defined(OS_MACOSX)
|
||||
|
||||
// Note that |render_widget_host_| will retrieve resize parameters from the
|
||||
// DelegatedFrameHost, so it must have SynchronizeVisualProperties called
|
||||
// after.
|
||||
if (resized && render_widget_host_)
|
||||
render_widget_host_->SynchronizeVisualProperties();
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::OnBeginFrameTimerTick() {
|
||||
const base::TimeTicks frame_time = base::TimeTicks::Now();
|
||||
const base::TimeDelta vsync_period =
|
||||
base::TimeDelta::FromMicroseconds(frame_rate_threshold_us_);
|
||||
SendBeginFrame(frame_time, vsync_period);
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::SendBeginFrame(base::TimeTicks frame_time,
|
||||
base::TimeDelta vsync_period) {
|
||||
TRACE_EVENT1("cef", "CefRenderWidgetHostViewOSR::SendBeginFrame",
|
||||
"frame_time_us", frame_time.ToInternalValue());
|
||||
|
||||
base::TimeTicks display_time = frame_time + vsync_period;
|
||||
|
||||
// TODO(brianderson): Use adaptive draw-time estimation.
|
||||
base::TimeDelta estimated_browser_composite_time =
|
||||
base::TimeDelta::FromMicroseconds(
|
||||
(1.0f * base::Time::kMicrosecondsPerSecond) / (3.0f * 60));
|
||||
|
||||
base::TimeTicks deadline = display_time - estimated_browser_composite_time;
|
||||
|
||||
const viz::BeginFrameArgs& begin_frame_args = viz::BeginFrameArgs::Create(
|
||||
BEGINFRAME_FROM_HERE, begin_frame_source_.source_id(),
|
||||
begin_frame_number_, frame_time, deadline, vsync_period,
|
||||
viz::BeginFrameArgs::NORMAL);
|
||||
DCHECK(begin_frame_args.IsValid());
|
||||
begin_frame_number_++;
|
||||
|
||||
if (render_widget_host_)
|
||||
render_widget_host_->ProgressFlingIfNeeded(frame_time);
|
||||
|
||||
if (renderer_compositor_frame_sink_) {
|
||||
renderer_compositor_frame_sink_->OnBeginFrame(begin_frame_args, {});
|
||||
}
|
||||
render_widget_host_->SynchronizeVisualProperties();
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::CancelWidget() {
|
||||
|
@ -1952,10 +1529,11 @@ void CefRenderWidgetHostViewOSR::OnGuestViewFrameSwapped(
|
|||
|
||||
void CefRenderWidgetHostViewOSR::InvalidateInternal(
|
||||
const gfx::Rect& bounds_in_pixels) {
|
||||
if (software_output_device_) {
|
||||
software_output_device_->OnPaint(bounds_in_pixels);
|
||||
} else if (copy_frame_generator_.get()) {
|
||||
copy_frame_generator_->GenerateCopyFrame(bounds_in_pixels);
|
||||
if (video_consumer_) {
|
||||
video_consumer_->SizeChanged();
|
||||
} else {
|
||||
OnPaint(bounds_in_pixels, host_display_client_->GetPixelSize(),
|
||||
host_display_client_->GetPixelMemory());
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1997,10 +1575,7 @@ viz::FrameSinkId CefRenderWidgetHostViewOSR::AllocateFrameSinkId(
|
|||
content::ImageTransportFactory::GetInstance();
|
||||
return is_guest_view_hack
|
||||
? factory->GetContextFactoryPrivate()->AllocateFrameSinkId()
|
||||
: viz::FrameSinkId(base::checked_cast<uint32_t>(
|
||||
render_widget_host_->GetProcess()->GetID()),
|
||||
base::checked_cast<uint32_t>(
|
||||
render_widget_host_->GetRoutingID()));
|
||||
: render_widget_host_->GetFrameSinkId();
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::UpdateBackgroundColorFromRenderer(
|
||||
|
|
|
@ -13,7 +13,8 @@
|
|||
|
||||
#include "include/cef_base.h"
|
||||
#include "include/cef_browser.h"
|
||||
#include "libcef/browser/browser_host_impl.h"
|
||||
|
||||
#include "libcef/browser/osr/host_display_client_osr.h"
|
||||
#include "libcef/browser/osr/motion_event_osr.h"
|
||||
|
||||
#include "base/memory/weak_ptr.h"
|
||||
|
@ -59,21 +60,12 @@ class BackingStore;
|
|||
class CursorManager;
|
||||
} // namespace content
|
||||
|
||||
class CefBeginFrameTimer;
|
||||
class CefBrowserHostImpl;
|
||||
class CefCopyFrameGenerator;
|
||||
class CefSoftwareOutputDeviceOSR;
|
||||
class CefVideoConsumerOSR;
|
||||
class CefWebContentsViewOSR;
|
||||
|
||||
#if defined(OS_MACOSX)
|
||||
#ifdef __OBJC__
|
||||
@class CALayer;
|
||||
@class NSWindow;
|
||||
#else
|
||||
class CALayer;
|
||||
class NSWindow;
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#if defined(USE_X11)
|
||||
class CefWindowX11;
|
||||
#endif
|
||||
|
@ -172,8 +164,6 @@ class CefRenderWidgetHostViewOSR : public content::RenderWidgetHostViewBase,
|
|||
void GetScreenInfo(content::ScreenInfo* results) override;
|
||||
void TransformPointToRootSurface(gfx::PointF* point) override;
|
||||
gfx::Rect GetBoundsInRootWindow() override;
|
||||
viz::ScopedSurfaceIdAllocator DidUpdateVisualProperties(
|
||||
const cc::RenderFrameMetadata& metadata) override;
|
||||
viz::SurfaceId GetCurrentSurfaceId() const override;
|
||||
content::BrowserAccessibilityManager* CreateBrowserAccessibilityManager(
|
||||
content::BrowserAccessibilityDelegate* delegate,
|
||||
|
@ -202,13 +192,12 @@ class CefRenderWidgetHostViewOSR : public content::RenderWidgetHostViewBase,
|
|||
const viz::FrameSinkId& GetFrameSinkId() const override;
|
||||
viz::FrameSinkId GetRootFrameSinkId() override;
|
||||
|
||||
// ui::ExternalBeginFrameClient implementation:
|
||||
// ui::ExternalBeginFrameClient implementation.
|
||||
void OnDisplayDidFinishFrame(const viz::BeginFrameAck& ack) override;
|
||||
void OnNeedsExternalBeginFrames(bool needs_begin_frames) override;
|
||||
|
||||
// ui::CompositorDelegate implementation.
|
||||
std::unique_ptr<viz::SoftwareOutputDevice> CreateSoftwareOutputDevice(
|
||||
ui::Compositor* compositor) override;
|
||||
std::unique_ptr<viz::HostDisplayClient> CreateHostDisplayClient() override;
|
||||
|
||||
// TextInputManager::Observer implementation.
|
||||
void OnUpdateTextInputStateCalled(
|
||||
|
@ -238,10 +227,12 @@ class CefRenderWidgetHostViewOSR : public content::RenderWidgetHostViewBase,
|
|||
void HoldResize();
|
||||
void ReleaseResize();
|
||||
|
||||
gfx::Size SizeInPixels();
|
||||
void OnPaint(const gfx::Rect& damage_rect,
|
||||
int bitmap_width,
|
||||
int bitmap_height,
|
||||
void* bitmap_pixels);
|
||||
const gfx::Size& pixel_size,
|
||||
const void* pixels);
|
||||
|
||||
void OnBeginFame(base::TimeTicks frame_time);
|
||||
|
||||
bool IsPopupWidget() const {
|
||||
return widget_type_ == content::WidgetType::kPopup;
|
||||
|
@ -277,12 +268,6 @@ class CefRenderWidgetHostViewOSR : public content::RenderWidgetHostViewBase,
|
|||
}
|
||||
ui::Layer* GetRootLayer() const;
|
||||
|
||||
#if defined(OS_MACOSX)
|
||||
content::BrowserCompositorMac* browser_compositor() const {
|
||||
return browser_compositor_.get();
|
||||
}
|
||||
#endif
|
||||
|
||||
void OnPresentCompositorFrame();
|
||||
|
||||
private:
|
||||
|
@ -292,10 +277,6 @@ class CefRenderWidgetHostViewOSR : public content::RenderWidgetHostViewBase,
|
|||
void SetDeviceScaleFactor();
|
||||
void ResizeRootLayer(bool force);
|
||||
|
||||
// Called by CefBeginFrameTimer to send a BeginFrame request.
|
||||
void OnBeginFrameTimerTick();
|
||||
void SendBeginFrame(base::TimeTicks frame_time, base::TimeDelta vsync_period);
|
||||
|
||||
void CancelWidget();
|
||||
|
||||
void OnScrollOffsetChanged();
|
||||
|
@ -323,21 +304,6 @@ class CefRenderWidgetHostViewOSR : public content::RenderWidgetHostViewBase,
|
|||
// opaqueness changes.
|
||||
void UpdateBackgroundColorFromRenderer(SkColor color);
|
||||
|
||||
#if defined(OS_MACOSX)
|
||||
display::Display GetDisplay();
|
||||
void OnDidUpdateVisualPropertiesComplete(
|
||||
const cc::RenderFrameMetadata& metadata);
|
||||
|
||||
friend class MacHelper;
|
||||
bool UpdateNSViewAndDisplay();
|
||||
#endif // defined(OS_MACOSX)
|
||||
|
||||
void PlatformCreateCompositorWidget(bool is_guest_view_hack);
|
||||
#if !defined(OS_MACOSX)
|
||||
void PlatformResizeCompositorWidget(const gfx::Size& size);
|
||||
#endif
|
||||
void PlatformDestroyCompositorWidget();
|
||||
|
||||
#if defined(USE_AURA)
|
||||
ui::PlatformCursor GetPlatformCursor(blink::WebCursorInfo::Type type);
|
||||
#endif
|
||||
|
@ -347,35 +313,21 @@ class CefRenderWidgetHostViewOSR : public content::RenderWidgetHostViewBase,
|
|||
|
||||
int frame_rate_threshold_us_;
|
||||
|
||||
#if !defined(OS_MACOSX)
|
||||
std::unique_ptr<ui::Compositor> compositor_;
|
||||
gfx::AcceleratedWidget compositor_widget_;
|
||||
std::unique_ptr<content::DelegatedFrameHost> delegated_frame_host_;
|
||||
std::unique_ptr<content::DelegatedFrameHostClient>
|
||||
delegated_frame_host_client_;
|
||||
std::unique_ptr<ui::Layer> root_layer_;
|
||||
viz::LocalSurfaceIdAllocation local_surface_id_allocation_;
|
||||
viz::ParentLocalSurfaceIdAllocator local_surface_id_allocator_;
|
||||
#endif
|
||||
viz::ParentLocalSurfaceIdAllocator compositor_local_surface_id_allocator_;
|
||||
|
||||
#if defined(OS_WIN)
|
||||
std::unique_ptr<gfx::WindowImpl> window_;
|
||||
#elif defined(OS_MACOSX)
|
||||
NSWindow* window_;
|
||||
CALayer* background_layer_;
|
||||
std::unique_ptr<content::BrowserCompositorMac> browser_compositor_;
|
||||
MacHelper* mac_helper_;
|
||||
#elif defined(USE_X11)
|
||||
CefWindowX11* window_;
|
||||
#if defined(USE_X11)
|
||||
std::unique_ptr<ui::XScopedCursor> invisible_cursor_;
|
||||
#endif
|
||||
|
||||
std::unique_ptr<content::CursorManager> cursor_manager_;
|
||||
|
||||
// Used to control the VSync rate in subprocesses when BeginFrame scheduling
|
||||
// is enabled.
|
||||
std::unique_ptr<CefBeginFrameTimer> begin_frame_timer_;
|
||||
|
||||
// Provides |source_id| for BeginFrameArgs that we create.
|
||||
viz::StubBeginFrameSource begin_frame_source_;
|
||||
uint64_t begin_frame_number_ = viz::BeginFrameArgs::kStartingFrameNumber;
|
||||
|
@ -384,12 +336,8 @@ class CefRenderWidgetHostViewOSR : public content::RenderWidgetHostViewBase,
|
|||
bool external_begin_frame_enabled_ = false;
|
||||
bool needs_external_begin_frames_ = false;
|
||||
|
||||
// Used for direct rendering from the compositor when GPU compositing is
|
||||
// disabled. This object is owned by the compositor.
|
||||
CefSoftwareOutputDeviceOSR* software_output_device_;
|
||||
|
||||
// Used for managing copy requests when GPU compositing is enabled.
|
||||
std::unique_ptr<CefCopyFrameGenerator> copy_frame_generator_;
|
||||
CefHostDisplayClientOSR* host_display_client_;
|
||||
std::unique_ptr<CefVideoConsumerOSR> video_consumer_;
|
||||
|
||||
bool hold_resize_;
|
||||
bool pending_resize_;
|
||||
|
|
|
@ -169,26 +169,6 @@ XCursorCache* cursor_cache = nullptr;
|
|||
} // namespace
|
||||
#endif // defined(USE_X11)
|
||||
|
||||
void CefRenderWidgetHostViewOSR::PlatformCreateCompositorWidget(
|
||||
bool is_guest_view_hack) {
|
||||
#if defined(USE_X11)
|
||||
// Create a hidden 1x1 window. It will delete itself on close.
|
||||
window_ = new CefWindowX11(NULL, None, gfx::Rect(0, 0, 1, 1), "");
|
||||
compositor_widget_ = window_->xwindow();
|
||||
#endif
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::PlatformResizeCompositorWidget(
|
||||
const gfx::Size&) {}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::PlatformDestroyCompositorWidget() {
|
||||
#if defined(USE_X11)
|
||||
DCHECK(window_);
|
||||
window_->Close();
|
||||
#endif
|
||||
compositor_widget_ = gfx::kNullAcceleratedWidget;
|
||||
}
|
||||
|
||||
ui::PlatformCursor CefRenderWidgetHostViewOSR::GetPlatformCursor(
|
||||
blink::WebCursorInfo::Type type) {
|
||||
#if defined(USE_X11)
|
||||
|
|
|
@ -1,172 +0,0 @@
|
|||
// Copyright (c) 2014 The Chromium Embedded Framework Authors.
|
||||
// Portions copyright (c) 2012 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 "libcef/browser/osr/render_widget_host_view_osr.h"
|
||||
|
||||
#include <algorithm>
|
||||
#include <limits>
|
||||
#include <utility>
|
||||
|
||||
#import <Cocoa/Cocoa.h>
|
||||
|
||||
#include "libcef/browser/browser_host_impl.h"
|
||||
|
||||
#include "base/compiler_specific.h"
|
||||
#include "base/strings/utf_string_conversions.h"
|
||||
#include "content/browser/renderer_host/render_widget_host_impl.h"
|
||||
#include "content/common/view_messages.h"
|
||||
#include "ui/accelerated_widget_mac/accelerated_widget_mac.h"
|
||||
#include "ui/display/screen.h"
|
||||
|
||||
class MacHelper : public content::BrowserCompositorMacClient,
|
||||
public ui::AcceleratedWidgetMacNSView {
|
||||
public:
|
||||
explicit MacHelper(CefRenderWidgetHostViewOSR* view) : view_(view) {}
|
||||
virtual ~MacHelper() {}
|
||||
|
||||
// BrowserCompositorMacClient methods:
|
||||
|
||||
SkColor BrowserCompositorMacGetGutterColor() const override {
|
||||
// When making an element on the page fullscreen the element's background
|
||||
// may not match the page's, so use black as the gutter color to avoid
|
||||
// flashes of brighter colors during the transition.
|
||||
if (view_->render_widget_host()->delegate() &&
|
||||
view_->render_widget_host()->delegate()->IsFullscreenForCurrentTab()) {
|
||||
return SK_ColorBLACK;
|
||||
}
|
||||
return *view_->GetBackgroundColor();
|
||||
}
|
||||
|
||||
void BrowserCompositorMacOnBeginFrame(base::TimeTicks frame_time) override {}
|
||||
|
||||
void OnFrameTokenChanged(uint32_t frame_token) override {
|
||||
view_->render_widget_host()->DidProcessFrame(frame_token);
|
||||
}
|
||||
|
||||
void DestroyCompositorForShutdown() override {}
|
||||
|
||||
bool OnBrowserCompositorSurfaceIdChanged() override {
|
||||
return view_->render_widget_host()->SynchronizeVisualProperties();
|
||||
}
|
||||
|
||||
std::vector<viz::SurfaceId> CollectSurfaceIdsForEviction() override {
|
||||
return view_->render_widget_host()->CollectSurfaceIdsForEviction();
|
||||
}
|
||||
|
||||
// AcceleratedWidgetMacNSView methods:
|
||||
|
||||
void AcceleratedWidgetCALayerParamsUpdated() override {}
|
||||
|
||||
private:
|
||||
// Guaranteed to outlive this object.
|
||||
CefRenderWidgetHostViewOSR* view_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(MacHelper);
|
||||
};
|
||||
|
||||
void CefRenderWidgetHostViewOSR::SetActive(bool active) {}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::ShowDefinitionForSelection() {}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::SpeakSelection() {}
|
||||
|
||||
viz::ScopedSurfaceIdAllocator
|
||||
CefRenderWidgetHostViewOSR::DidUpdateVisualProperties(
|
||||
const cc::RenderFrameMetadata& metadata) {
|
||||
base::OnceCallback<void()> allocation_task = base::BindOnce(
|
||||
base::IgnoreResult(
|
||||
&CefRenderWidgetHostViewOSR::OnDidUpdateVisualPropertiesComplete),
|
||||
weak_ptr_factory_.GetWeakPtr(), metadata);
|
||||
return browser_compositor_->GetScopedRendererSurfaceIdAllocator(
|
||||
std::move(allocation_task));
|
||||
}
|
||||
|
||||
display::Display CefRenderWidgetHostViewOSR::GetDisplay() {
|
||||
content::ScreenInfo screen_info;
|
||||
GetScreenInfo(&screen_info);
|
||||
|
||||
// Start with a reasonable display representation.
|
||||
display::Display display =
|
||||
display::Screen::GetScreen()->GetDisplayNearestView(nullptr);
|
||||
|
||||
// Populate attributes based on |screen_info|.
|
||||
display.set_bounds(screen_info.rect);
|
||||
display.set_work_area(screen_info.available_rect);
|
||||
display.set_device_scale_factor(screen_info.device_scale_factor);
|
||||
display.set_color_space(screen_info.color_space);
|
||||
display.set_color_depth(screen_info.depth);
|
||||
display.set_depth_per_component(screen_info.depth_per_component);
|
||||
display.set_is_monochrome(screen_info.is_monochrome);
|
||||
display.SetRotationAsDegree(screen_info.orientation_angle);
|
||||
|
||||
return display;
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::OnDidUpdateVisualPropertiesComplete(
|
||||
const cc::RenderFrameMetadata& metadata) {
|
||||
DCHECK_EQ(current_device_scale_factor_, metadata.device_scale_factor);
|
||||
browser_compositor_->UpdateSurfaceFromChild(
|
||||
metadata.device_scale_factor, metadata.viewport_size_in_pixels,
|
||||
metadata.local_surface_id_allocation.value_or(
|
||||
viz::LocalSurfaceIdAllocation()));
|
||||
}
|
||||
|
||||
const viz::LocalSurfaceIdAllocation&
|
||||
CefRenderWidgetHostViewOSR::GetLocalSurfaceIdAllocation() const {
|
||||
return browser_compositor_->GetRendererLocalSurfaceIdAllocation();
|
||||
}
|
||||
|
||||
ui::Compositor* CefRenderWidgetHostViewOSR::GetCompositor() const {
|
||||
return browser_compositor_->GetCompositor();
|
||||
}
|
||||
|
||||
ui::Layer* CefRenderWidgetHostViewOSR::GetRootLayer() const {
|
||||
return browser_compositor_->GetRootLayer();
|
||||
}
|
||||
|
||||
content::DelegatedFrameHost* CefRenderWidgetHostViewOSR::GetDelegatedFrameHost()
|
||||
const {
|
||||
return browser_compositor_->GetDelegatedFrameHost();
|
||||
}
|
||||
|
||||
bool CefRenderWidgetHostViewOSR::UpdateNSViewAndDisplay() {
|
||||
return browser_compositor_->UpdateSurfaceFromNSView(
|
||||
GetRootLayer()->bounds().size(), GetDisplay());
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::PlatformCreateCompositorWidget(
|
||||
bool is_guest_view_hack) {
|
||||
// Create a borderless non-visible 1x1 window.
|
||||
window_ = [[NSWindow alloc] initWithContentRect:NSMakeRect(0, 0, 1, 1)
|
||||
styleMask:NSBorderlessWindowMask
|
||||
backing:NSBackingStoreBuffered
|
||||
defer:NO];
|
||||
|
||||
// Create a CALayer which is used by BrowserCompositorViewMac for rendering.
|
||||
background_layer_ = [[[CALayer alloc] init] retain];
|
||||
[background_layer_ setBackgroundColor:CGColorGetConstantColor(kCGColorClear)];
|
||||
NSView* content_view = [window_ contentView];
|
||||
[content_view setLayer:background_layer_];
|
||||
[content_view setWantsLayer:YES];
|
||||
|
||||
mac_helper_ = new MacHelper(this);
|
||||
browser_compositor_.reset(new content::BrowserCompositorMac(
|
||||
mac_helper_, mac_helper_, render_widget_host_->is_hidden(), GetDisplay(),
|
||||
AllocateFrameSinkId(is_guest_view_hack)));
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::PlatformDestroyCompositorWidget() {
|
||||
DCHECK(window_);
|
||||
|
||||
[window_ close];
|
||||
window_ = nil;
|
||||
[background_layer_ release];
|
||||
background_layer_ = nil;
|
||||
|
||||
browser_compositor_.reset();
|
||||
|
||||
delete mac_helper_;
|
||||
mac_helper_ = nullptr;
|
||||
}
|
|
@ -142,25 +142,6 @@ bool IsSystemCursorID(LPCWSTR cursor_id) {
|
|||
|
||||
} // namespace
|
||||
|
||||
void CefRenderWidgetHostViewOSR::PlatformCreateCompositorWidget(
|
||||
bool is_guest_view_hack) {
|
||||
DCHECK(!window_);
|
||||
window_.reset(new CefCompositorHostWin());
|
||||
compositor_widget_ = window_->hwnd();
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::PlatformResizeCompositorWidget(
|
||||
const gfx::Size& size) {
|
||||
DCHECK(window_);
|
||||
SetWindowPos(window_->hwnd(), NULL, 0, 0, size.width(), size.height(),
|
||||
SWP_NOMOVE | SWP_NOZORDER | SWP_NOREDRAW | SWP_NOACTIVATE);
|
||||
}
|
||||
|
||||
void CefRenderWidgetHostViewOSR::PlatformDestroyCompositorWidget() {
|
||||
window_.reset(NULL);
|
||||
compositor_widget_ = gfx::kNullAcceleratedWidget;
|
||||
}
|
||||
|
||||
ui::PlatformCursor CefRenderWidgetHostViewOSR::GetPlatformCursor(
|
||||
blink::WebCursorInfo::Type type) {
|
||||
HMODULE module_handle = NULL;
|
||||
|
|
|
@ -1,108 +0,0 @@
|
|||
// Copyright (c) 2014 The Chromium Embedded Framework Authors.
|
||||
// Portions copyright (c) 2014 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 "libcef/browser/osr/software_output_device_osr.h"
|
||||
|
||||
#include "libcef/browser/browser_host_impl.h"
|
||||
#include "libcef/browser/osr/render_widget_host_view_osr.h"
|
||||
#include "libcef/browser/thread_util.h"
|
||||
|
||||
#include "third_party/skia/src/core/SkDevice.h"
|
||||
#include "ui/compositor/compositor.h"
|
||||
#include "ui/gfx/skia_util.h"
|
||||
|
||||
CefSoftwareOutputDeviceOSR::CefSoftwareOutputDeviceOSR(
|
||||
ui::Compositor* compositor,
|
||||
bool transparent,
|
||||
const OnPaintCallback& callback)
|
||||
: transparent_(transparent), callback_(callback), active_(false) {
|
||||
CEF_REQUIRE_UIT();
|
||||
DCHECK(!callback_.is_null());
|
||||
}
|
||||
|
||||
CefSoftwareOutputDeviceOSR::~CefSoftwareOutputDeviceOSR() {
|
||||
CEF_REQUIRE_UIT();
|
||||
}
|
||||
|
||||
void CefSoftwareOutputDeviceOSR::Resize(const gfx::Size& viewport_pixel_size,
|
||||
float scale_factor) {
|
||||
CEF_REQUIRE_UIT();
|
||||
|
||||
if (viewport_pixel_size_ == viewport_pixel_size)
|
||||
return;
|
||||
|
||||
viewport_pixel_size_ = viewport_pixel_size;
|
||||
|
||||
canvas_.reset(NULL);
|
||||
bitmap_.reset(new SkBitmap);
|
||||
bitmap_->allocN32Pixels(viewport_pixel_size.width(),
|
||||
viewport_pixel_size.height(), !transparent_);
|
||||
if (bitmap_->drawsNothing()) {
|
||||
NOTREACHED();
|
||||
bitmap_.reset(NULL);
|
||||
return;
|
||||
}
|
||||
|
||||
if (transparent_)
|
||||
bitmap_->eraseARGB(0, 0, 0, 0);
|
||||
|
||||
canvas_.reset(new SkCanvas(*bitmap_.get()));
|
||||
}
|
||||
|
||||
SkCanvas* CefSoftwareOutputDeviceOSR::BeginPaint(const gfx::Rect& damage_rect) {
|
||||
CEF_REQUIRE_UIT();
|
||||
DCHECK(canvas_.get());
|
||||
DCHECK(bitmap_.get());
|
||||
|
||||
damage_rect_ = damage_rect;
|
||||
|
||||
return canvas_.get();
|
||||
}
|
||||
|
||||
void CefSoftwareOutputDeviceOSR::EndPaint() {
|
||||
CEF_REQUIRE_UIT();
|
||||
DCHECK(canvas_.get());
|
||||
DCHECK(bitmap_.get());
|
||||
|
||||
if (!bitmap_.get())
|
||||
return;
|
||||
|
||||
viz::SoftwareOutputDevice::EndPaint();
|
||||
|
||||
if (active_)
|
||||
OnPaint(damage_rect_);
|
||||
}
|
||||
|
||||
void CefSoftwareOutputDeviceOSR::SetActive(bool active) {
|
||||
if (active == active_)
|
||||
return;
|
||||
active_ = active;
|
||||
|
||||
// Call OnPaint immediately if deactivated while a damage rect is pending.
|
||||
if (!active_ && !pending_damage_rect_.IsEmpty())
|
||||
OnPaint(pending_damage_rect_);
|
||||
}
|
||||
|
||||
void CefSoftwareOutputDeviceOSR::Invalidate(const gfx::Rect& damage_rect) {
|
||||
if (pending_damage_rect_.IsEmpty())
|
||||
pending_damage_rect_ = damage_rect;
|
||||
else
|
||||
pending_damage_rect_.Union(damage_rect);
|
||||
}
|
||||
|
||||
void CefSoftwareOutputDeviceOSR::OnPaint(const gfx::Rect& damage_rect) {
|
||||
gfx::Rect rect = damage_rect;
|
||||
if (!pending_damage_rect_.IsEmpty()) {
|
||||
rect.Union(pending_damage_rect_);
|
||||
pending_damage_rect_.SetRect(0, 0, 0, 0);
|
||||
}
|
||||
|
||||
rect.Intersect(gfx::Rect(viewport_pixel_size_));
|
||||
if (rect.IsEmpty())
|
||||
return;
|
||||
|
||||
callback_.Run(rect, bitmap_->width(), bitmap_->height(),
|
||||
bitmap_->getPixels());
|
||||
}
|
|
@ -1,54 +0,0 @@
|
|||
// Copyright (c) 2014 The Chromium Embedded Framework Authors.
|
||||
// Portions copyright (c) 2014 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.
|
||||
|
||||
#ifndef CEF_LIBCEF_BROWSER_OSR_SOFTWARE_OUTPUT_DEVICE_OSR_H_
|
||||
#define CEF_LIBCEF_BROWSER_OSR_SOFTWARE_OUTPUT_DEVICE_OSR_H_
|
||||
|
||||
#include "base/callback.h"
|
||||
#include "components/viz/service/display/software_output_device.h"
|
||||
|
||||
namespace ui {
|
||||
class Compositor;
|
||||
}
|
||||
|
||||
// Device implementation for direct software rendering via DelegatedFrameHost.
|
||||
// All Rect/Size values are in pixels.
|
||||
class CefSoftwareOutputDeviceOSR : public viz::SoftwareOutputDevice {
|
||||
public:
|
||||
typedef base::Callback<void(const gfx::Rect&, int, int, void*)>
|
||||
OnPaintCallback;
|
||||
|
||||
CefSoftwareOutputDeviceOSR(ui::Compositor* compositor,
|
||||
bool transparent,
|
||||
const OnPaintCallback& callback);
|
||||
~CefSoftwareOutputDeviceOSR() override;
|
||||
|
||||
// viz::SoftwareOutputDevice implementation.
|
||||
void Resize(const gfx::Size& viewport_pixel_size,
|
||||
float scale_factor) override;
|
||||
SkCanvas* BeginPaint(const gfx::Rect& damage_rect) override;
|
||||
void EndPaint() override;
|
||||
|
||||
void SetActive(bool active);
|
||||
|
||||
// Include |damage_rect| the next time OnPaint is called.
|
||||
void Invalidate(const gfx::Rect& damage_rect);
|
||||
|
||||
// Deliver the OnPaint notification immediately.
|
||||
void OnPaint(const gfx::Rect& damage_rect);
|
||||
|
||||
private:
|
||||
const bool transparent_;
|
||||
const OnPaintCallback callback_;
|
||||
|
||||
bool active_;
|
||||
std::unique_ptr<SkCanvas> canvas_;
|
||||
std::unique_ptr<SkBitmap> bitmap_;
|
||||
gfx::Rect pending_damage_rect_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(CefSoftwareOutputDeviceOSR);
|
||||
};
|
||||
|
||||
#endif // CEF_LIBCEF_BROWSER_OSR_SOFTWARE_OUTPUT_DEVICE_OSR_H_
|
|
@ -0,0 +1,151 @@
|
|||
// Copyright 2014 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 "cef/libcef/browser/osr/software_output_device_proxy.h"
|
||||
|
||||
#include "base/memory/shared_memory.h"
|
||||
#include "components/viz/common/resources/resource_sizes.h"
|
||||
#include "mojo/public/cpp/base/shared_memory_utils.h"
|
||||
#include "mojo/public/cpp/system/platform_handle.h"
|
||||
#include "skia/ext/platform_canvas.h"
|
||||
#include "third_party/skia/include/core/SkCanvas.h"
|
||||
#include "ui/gfx/skia_util.h"
|
||||
|
||||
#if defined(OS_WIN)
|
||||
#include <windows.h>
|
||||
#include "skia/ext/skia_utils_win.h"
|
||||
#include "ui/gfx/gdi_util.h"
|
||||
#include "ui/gfx/win/hwnd_util.h"
|
||||
#endif
|
||||
|
||||
namespace viz {
|
||||
|
||||
SoftwareOutputDeviceProxy::~SoftwareOutputDeviceProxy() = default;
|
||||
|
||||
SoftwareOutputDeviceProxy::SoftwareOutputDeviceProxy(
|
||||
mojom::LayeredWindowUpdaterPtr layered_window_updater)
|
||||
: layered_window_updater_(std::move(layered_window_updater)) {
|
||||
DCHECK(layered_window_updater_.is_bound());
|
||||
}
|
||||
|
||||
void SoftwareOutputDeviceProxy::OnSwapBuffers(
|
||||
SwapBuffersCallback swap_ack_callback) {
|
||||
DCHECK_CALLED_ON_VALID_THREAD(thread_checker_);
|
||||
DCHECK(swap_ack_callback_.is_null());
|
||||
|
||||
// We aren't waiting on DrawAck() and can immediately run the callback.
|
||||
if (!waiting_on_draw_ack_) {
|
||||
task_runner_->PostTask(
|
||||
FROM_HERE,
|
||||
base::BindOnce(std::move(swap_ack_callback), viewport_pixel_size_));
|
||||
return;
|
||||
}
|
||||
|
||||
swap_ack_callback_ =
|
||||
base::BindOnce(std::move(swap_ack_callback), viewport_pixel_size_);
|
||||
}
|
||||
|
||||
void SoftwareOutputDeviceProxy::Resize(const gfx::Size& viewport_pixel_size,
|
||||
float scale_factor) {
|
||||
DCHECK_CALLED_ON_VALID_THREAD(thread_checker_);
|
||||
DCHECK(!in_paint_);
|
||||
|
||||
if (viewport_pixel_size_ == viewport_pixel_size)
|
||||
return;
|
||||
|
||||
viewport_pixel_size_ = viewport_pixel_size;
|
||||
|
||||
canvas_.reset();
|
||||
|
||||
size_t required_bytes;
|
||||
if (!ResourceSizes::MaybeSizeInBytes(
|
||||
viewport_pixel_size_, ResourceFormat::RGBA_8888, &required_bytes)) {
|
||||
DLOG(ERROR) << "Invalid viewport size " << viewport_pixel_size_.ToString();
|
||||
return;
|
||||
}
|
||||
|
||||
#if !defined(OS_WIN)
|
||||
auto shm = mojo::CreateReadOnlySharedMemoryRegion(required_bytes);
|
||||
if (!shm.IsValid()) {
|
||||
DLOG(ERROR) << "Failed to allocate " << required_bytes << " bytes";
|
||||
return;
|
||||
}
|
||||
|
||||
shm_ = std::move(shm.mapping);
|
||||
if (!shm_.IsValid()) {
|
||||
DLOG(ERROR) << "Failed to map " << required_bytes << " bytes";
|
||||
return;
|
||||
}
|
||||
|
||||
canvas_ = skia::CreatePlatformCanvasWithPixels(
|
||||
viewport_pixel_size_.width(), viewport_pixel_size_.height(), false,
|
||||
static_cast<uint8_t*>(shm_.memory()), skia::CRASH_ON_FAILURE);
|
||||
|
||||
mojo::ScopedSharedBufferHandle scoped_handle =
|
||||
mojo::WrapReadOnlySharedMemoryRegion(std::move(shm.region));
|
||||
#else
|
||||
base::SharedMemory shm;
|
||||
if (!shm.CreateAnonymous(required_bytes)) {
|
||||
DLOG(ERROR) << "Failed to allocate " << required_bytes << " bytes";
|
||||
return;
|
||||
}
|
||||
canvas_ = skia::CreatePlatformCanvasWithSharedSection(
|
||||
viewport_pixel_size_.width(), viewport_pixel_size_.height(), false,
|
||||
shm.handle().GetHandle(), skia::CRASH_ON_FAILURE);
|
||||
|
||||
// Transfer handle ownership to the browser process.
|
||||
mojo::ScopedSharedBufferHandle scoped_handle = mojo::WrapSharedMemoryHandle(
|
||||
shm.GetReadOnlyHandle(), required_bytes,
|
||||
mojo::UnwrappedSharedMemoryHandleProtection::kReadOnly);
|
||||
#endif
|
||||
|
||||
layered_window_updater_->OnAllocatedSharedMemory(viewport_pixel_size_,
|
||||
std::move(scoped_handle));
|
||||
}
|
||||
|
||||
SkCanvas* SoftwareOutputDeviceProxy::BeginPaint(const gfx::Rect& damage_rect) {
|
||||
DCHECK_CALLED_ON_VALID_THREAD(thread_checker_);
|
||||
DCHECK(!in_paint_);
|
||||
|
||||
damage_rect_ = damage_rect;
|
||||
in_paint_ = true;
|
||||
|
||||
return canvas_.get();
|
||||
}
|
||||
|
||||
void SoftwareOutputDeviceProxy::EndPaint() {
|
||||
DCHECK_CALLED_ON_VALID_THREAD(thread_checker_);
|
||||
DCHECK(in_paint_);
|
||||
DCHECK(!waiting_on_draw_ack_);
|
||||
|
||||
in_paint_ = false;
|
||||
|
||||
gfx::Rect intersected_damage_rect = damage_rect_;
|
||||
intersected_damage_rect.Intersect(gfx::Rect(viewport_pixel_size_));
|
||||
if (intersected_damage_rect.IsEmpty())
|
||||
return;
|
||||
|
||||
if (!canvas_)
|
||||
return;
|
||||
|
||||
layered_window_updater_->Draw(
|
||||
damage_rect_, base::BindOnce(&SoftwareOutputDeviceProxy::DrawAck,
|
||||
base::Unretained(this)));
|
||||
waiting_on_draw_ack_ = true;
|
||||
|
||||
TRACE_EVENT_ASYNC_BEGIN0("viz", "SoftwareOutputDeviceProxy::Draw", this);
|
||||
}
|
||||
|
||||
void SoftwareOutputDeviceProxy::DrawAck() {
|
||||
DCHECK_CALLED_ON_VALID_THREAD(thread_checker_);
|
||||
DCHECK(waiting_on_draw_ack_);
|
||||
DCHECK(!swap_ack_callback_.is_null());
|
||||
|
||||
TRACE_EVENT_ASYNC_END0("viz", "SoftwareOutputDeviceProxy::Draw", this);
|
||||
|
||||
waiting_on_draw_ack_ = false;
|
||||
std::move(swap_ack_callback_).Run();
|
||||
}
|
||||
|
||||
} // namespace viz
|
|
@ -0,0 +1,52 @@
|
|||
#ifndef CEF_LIBCEF_BROWSER_OSR_SOFTWARE_OUTPUT_DEVICE_PROXY_H_
|
||||
#define CEF_LIBCEF_BROWSER_OSR_SOFTWARE_OUTPUT_DEVICE_PROXY_H_
|
||||
|
||||
#include "base/memory/shared_memory_mapping.h"
|
||||
#include "base/threading/thread_checker.h"
|
||||
#include "components/viz/service/display/software_output_device.h"
|
||||
#include "components/viz/service/viz_service_export.h"
|
||||
#include "services/viz/privileged/interfaces/compositing/display_private.mojom.h"
|
||||
#include "services/viz/privileged/interfaces/compositing/layered_window_updater.mojom.h"
|
||||
|
||||
namespace viz {
|
||||
|
||||
// SoftwareOutputDevice implementation that draws indirectly. An
|
||||
// implementation of mojom::LayeredWindowUpdater in the browser process
|
||||
// handles the actual drawing. Pixel backing is in SharedMemory so no copying
|
||||
// between processes is required.
|
||||
class VIZ_SERVICE_EXPORT SoftwareOutputDeviceProxy
|
||||
: public SoftwareOutputDevice {
|
||||
public:
|
||||
explicit SoftwareOutputDeviceProxy(
|
||||
mojom::LayeredWindowUpdaterPtr layered_window_updater);
|
||||
~SoftwareOutputDeviceProxy() override;
|
||||
|
||||
// SoftwareOutputDevice implementation.
|
||||
void OnSwapBuffers(SwapBuffersCallback swap_ack_callback) override;
|
||||
|
||||
// SoftwareOutputDeviceBase implementation.
|
||||
void Resize(const gfx::Size& viewport_pixel_size,
|
||||
float scale_factor) override;
|
||||
SkCanvas* BeginPaint(const gfx::Rect& damage_rect) override;
|
||||
void EndPaint() override;
|
||||
|
||||
private:
|
||||
// Runs |swap_ack_callback_| after draw has happened.
|
||||
void DrawAck();
|
||||
|
||||
mojom::LayeredWindowUpdaterPtr layered_window_updater_;
|
||||
|
||||
std::unique_ptr<SkCanvas> canvas_;
|
||||
bool waiting_on_draw_ack_ = false;
|
||||
bool in_paint_ = false;
|
||||
base::OnceClosure swap_ack_callback_;
|
||||
base::WritableSharedMemoryMapping shm_;
|
||||
|
||||
THREAD_CHECKER(thread_checker_);
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(SoftwareOutputDeviceProxy);
|
||||
};
|
||||
|
||||
} // namespace viz
|
||||
|
||||
#endif // CEF_LIBCEF_BROWSER_OSR_SOFTWARE_OUTPUT_DEVICE_PROXY_H_
|
|
@ -0,0 +1,89 @@
|
|||
// Copyright (c) 2015 GitHub, Inc.
|
||||
// Use of this source code is governed by the MIT license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
#include "libcef/browser/osr/video_consumer_osr.h"
|
||||
|
||||
#include "libcef/browser/browser_host_impl.h"
|
||||
#include "libcef/browser/osr/render_widget_host_view_osr.h"
|
||||
|
||||
#include "media/base/video_frame_metadata.h"
|
||||
#include "media/capture/mojom/video_capture_types.mojom.h"
|
||||
#include "ui/gfx/skbitmap_operations.h"
|
||||
|
||||
CefVideoConsumerOSR::CefVideoConsumerOSR(CefRenderWidgetHostViewOSR* view)
|
||||
: view_(view),
|
||||
video_capturer_(view->CreateVideoCapturer()),
|
||||
weak_ptr_factory_(this) {
|
||||
const gfx::Size view_size = view_->SizeInPixels();
|
||||
video_capturer_->SetResolutionConstraints(view_size, view_size, true);
|
||||
video_capturer_->SetAutoThrottlingEnabled(false);
|
||||
video_capturer_->SetMinSizeChangePeriod(base::TimeDelta());
|
||||
video_capturer_->SetFormat(media::PIXEL_FORMAT_ARGB,
|
||||
gfx::ColorSpace::CreateREC709());
|
||||
}
|
||||
|
||||
CefVideoConsumerOSR::~CefVideoConsumerOSR() = default;
|
||||
|
||||
void CefVideoConsumerOSR::SetActive(bool active) {
|
||||
if (active) {
|
||||
video_capturer_->Start(this);
|
||||
} else {
|
||||
video_capturer_->Stop();
|
||||
}
|
||||
}
|
||||
|
||||
void CefVideoConsumerOSR::SetFrameRate(base::TimeDelta frame_rate) {
|
||||
video_capturer_->SetMinCapturePeriod(frame_rate);
|
||||
}
|
||||
|
||||
void CefVideoConsumerOSR::SizeChanged() {
|
||||
const gfx::Size view_size = view_->SizeInPixels();
|
||||
video_capturer_->SetResolutionConstraints(view_size, view_size, true);
|
||||
video_capturer_->RequestRefreshFrame();
|
||||
}
|
||||
|
||||
void CefVideoConsumerOSR::OnFrameCaptured(
|
||||
base::ReadOnlySharedMemoryRegion data,
|
||||
::media::mojom::VideoFrameInfoPtr info,
|
||||
const gfx::Rect& content_rect,
|
||||
viz::mojom::FrameSinkVideoConsumerFrameCallbacksPtr callbacks) {
|
||||
const gfx::Size view_size = view_->SizeInPixels();
|
||||
if (view_size != content_rect.size()) {
|
||||
video_capturer_->SetResolutionConstraints(view_size, view_size, true);
|
||||
video_capturer_->RequestRefreshFrame();
|
||||
return;
|
||||
}
|
||||
|
||||
if (!data.IsValid()) {
|
||||
callbacks->Done();
|
||||
return;
|
||||
}
|
||||
base::ReadOnlySharedMemoryMapping mapping = data.Map();
|
||||
if (!mapping.IsValid()) {
|
||||
DLOG(ERROR) << "Shared memory mapping failed.";
|
||||
return;
|
||||
}
|
||||
if (mapping.size() <
|
||||
media::VideoFrame::AllocationSize(info->pixel_format, info->coded_size)) {
|
||||
DLOG(ERROR) << "Shared memory size was less than expected.";
|
||||
return;
|
||||
}
|
||||
|
||||
// The SkBitmap's pixels will be marked as immutable, but the installPixels()
|
||||
// API requires a non-const pointer. So, cast away the const.
|
||||
void* const pixels = const_cast<void*>(mapping.memory());
|
||||
|
||||
media::VideoFrameMetadata metadata;
|
||||
metadata.MergeInternalValuesFrom(info->metadata);
|
||||
gfx::Rect damage_rect;
|
||||
|
||||
if (!metadata.GetRect(media::VideoFrameMetadata::CAPTURE_UPDATE_RECT,
|
||||
&damage_rect)) {
|
||||
damage_rect = content_rect;
|
||||
}
|
||||
|
||||
view_->OnPaint(damage_rect, content_rect.size(), pixels);
|
||||
}
|
||||
|
||||
void CefVideoConsumerOSR::OnStopped() {}
|
|
@ -0,0 +1,36 @@
|
|||
#ifndef LIBCEF_BROWSER_OSR_VIDEO_CONSUMER_OSR_H_
|
||||
#define LIBCEF_BROWSER_OSR_VIDEO_CONSUMER_OSR_H_
|
||||
|
||||
#include "base/callback.h"
|
||||
#include "base/memory/weak_ptr.h"
|
||||
#include "components/viz/host/client_frame_sink_video_capturer.h"
|
||||
|
||||
class CefRenderWidgetHostViewOSR;
|
||||
|
||||
class CefVideoConsumerOSR : public viz::mojom::FrameSinkVideoConsumer {
|
||||
public:
|
||||
explicit CefVideoConsumerOSR(CefRenderWidgetHostViewOSR* view);
|
||||
~CefVideoConsumerOSR() override;
|
||||
|
||||
void SetActive(bool active);
|
||||
void SetFrameRate(base::TimeDelta frame_rate);
|
||||
void SizeChanged();
|
||||
|
||||
private:
|
||||
// viz::mojom::FrameSinkVideoConsumer implementation.
|
||||
void OnFrameCaptured(
|
||||
base::ReadOnlySharedMemoryRegion data,
|
||||
::media::mojom::VideoFrameInfoPtr info,
|
||||
const gfx::Rect& content_rect,
|
||||
viz::mojom::FrameSinkVideoConsumerFrameCallbacksPtr callbacks) override;
|
||||
void OnStopped() override;
|
||||
|
||||
CefRenderWidgetHostViewOSR* const view_;
|
||||
std::unique_ptr<viz::ClientFrameSinkVideoCapturer> video_capturer_;
|
||||
|
||||
base::WeakPtrFactory<CefVideoConsumerOSR> weak_ptr_factory_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(CefVideoConsumerOSR);
|
||||
};
|
||||
|
||||
#endif // LIBCEF_BROWSER_OSR_VIDEO_CONSUMER_OSR_H_
|
|
@ -558,15 +558,6 @@ bool CefMainDelegate::BasicStartupComplete(int* exit_code) {
|
|||
|
||||
std::vector<std::string> disable_features;
|
||||
|
||||
if (settings.windowless_rendering_enabled) {
|
||||
// Disable VizDisplayCompositor when OSR is enabled until
|
||||
// we have implemented Viz support
|
||||
if (features::kVizDisplayCompositor.default_state ==
|
||||
base::FEATURE_ENABLED_BY_DEFAULT) {
|
||||
disable_features.push_back(features::kVizDisplayCompositor.name);
|
||||
}
|
||||
}
|
||||
|
||||
if (network::features::kOutOfBlinkCors.default_state ==
|
||||
base::FEATURE_ENABLED_BY_DEFAULT) {
|
||||
// TODO: Add support for out-of-Blink CORS (see issue #2716)
|
||||
|
|
|
@ -383,11 +383,6 @@ patches = [
|
|||
# https://bitbucket.org/chromiumembedded/cef/issues/2540
|
||||
'name': 'mac_fling_scheduler_2540',
|
||||
},
|
||||
{
|
||||
# Support rendering to a hardware GL/D3D texture/surface provided by the client
|
||||
# https://bitbucket.org/chromiumembedded/cef/issues/1006
|
||||
'name': 'external_textures_1006',
|
||||
},
|
||||
{
|
||||
# Linux: Use poll instead of select to fix crash during startup.
|
||||
# https://bitbucket.org/chromiumembedded/cef/issues/2466
|
||||
|
@ -460,5 +455,10 @@ patches = [
|
|||
# Shutdown for all Profiles before local_state deletion.
|
||||
# This crash was introduced by https://crrev.com/7d032b378c.
|
||||
'name': 'chrome_pref_watcher',
|
||||
}
|
||||
},
|
||||
{
|
||||
# Add support for OSR rendering with Viz.
|
||||
# https://bitbucket.org/chromiumembedded/cef/issues/2575
|
||||
'name': 'viz_osr_2575',
|
||||
}
|
||||
]
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,263 @@
|
|||
diff --git components/viz/host/host_display_client.cc components/viz/host/host_display_client.cc
|
||||
index f5e18df4e06e..58a8e8ef125b 100644
|
||||
--- components/viz/host/host_display_client.cc
|
||||
+++ components/viz/host/host_display_client.cc
|
||||
@@ -46,9 +46,14 @@ void HostDisplayClient::OnDisplayReceivedCALayerParams(
|
||||
}
|
||||
#endif
|
||||
|
||||
-#if defined(OS_WIN)
|
||||
+void HostDisplayClient::UseProxyOutputDevice(
|
||||
+ UseProxyOutputDeviceCallback callback) {
|
||||
+ std::move(callback).Run(false);
|
||||
+}
|
||||
+
|
||||
void HostDisplayClient::CreateLayeredWindowUpdater(
|
||||
mojom::LayeredWindowUpdaterRequest request) {
|
||||
+#if OS_WIN
|
||||
if (!NeedsToUseLayerWindow(widget_)) {
|
||||
DLOG(ERROR) << "HWND shouldn't be using a layered window";
|
||||
return;
|
||||
@@ -56,8 +61,8 @@ void HostDisplayClient::CreateLayeredWindowUpdater(
|
||||
|
||||
layered_window_updater_ =
|
||||
std::make_unique<LayeredWindowUpdaterImpl>(widget_, std::move(request));
|
||||
-}
|
||||
#endif
|
||||
+}
|
||||
|
||||
#if defined(USE_X11)
|
||||
void HostDisplayClient::DidCompleteSwapWithNewSize(const gfx::Size& size) {
|
||||
diff --git components/viz/host/host_display_client.h components/viz/host/host_display_client.h
|
||||
index 5e5c5da4a3cf..30eca49765bd 100644
|
||||
--- components/viz/host/host_display_client.h
|
||||
+++ components/viz/host/host_display_client.h
|
||||
@@ -30,17 +30,17 @@ class VIZ_HOST_EXPORT HostDisplayClient : public mojom::DisplayClient {
|
||||
mojom::DisplayClientPtr GetBoundPtr(
|
||||
scoped_refptr<base::SingleThreadTaskRunner> task_runner);
|
||||
|
||||
- private:
|
||||
+ protected:
|
||||
// mojom::DisplayClient implementation:
|
||||
+ void UseProxyOutputDevice(UseProxyOutputDeviceCallback callback) override;
|
||||
+
|
||||
#if defined(OS_MACOSX)
|
||||
void OnDisplayReceivedCALayerParams(
|
||||
const gfx::CALayerParams& ca_layer_params) override;
|
||||
#endif
|
||||
|
||||
-#if defined(OS_WIN)
|
||||
void CreateLayeredWindowUpdater(
|
||||
mojom::LayeredWindowUpdaterRequest request) override;
|
||||
-#endif
|
||||
|
||||
#if defined(USE_X11)
|
||||
void DidCompleteSwapWithNewSize(const gfx::Size& size) override;
|
||||
diff --git components/viz/host/layered_window_updater_impl.cc components/viz/host/layered_window_updater_impl.cc
|
||||
index d3a49ed8be8d..38a927b8f734 100644
|
||||
--- components/viz/host/layered_window_updater_impl.cc
|
||||
+++ components/viz/host/layered_window_updater_impl.cc
|
||||
@@ -47,7 +47,7 @@ void LayeredWindowUpdaterImpl::OnAllocatedSharedMemory(
|
||||
shm_handle.Close();
|
||||
}
|
||||
|
||||
-void LayeredWindowUpdaterImpl::Draw(DrawCallback draw_callback) {
|
||||
+void LayeredWindowUpdaterImpl::Draw(const gfx::Rect& damage_rect, DrawCallback draw_callback) {
|
||||
TRACE_EVENT0("viz", "LayeredWindowUpdaterImpl::Draw");
|
||||
|
||||
if (!canvas_) {
|
||||
diff --git components/viz/host/layered_window_updater_impl.h components/viz/host/layered_window_updater_impl.h
|
||||
index 93c52d2b928c..4dc645e770a2 100644
|
||||
--- components/viz/host/layered_window_updater_impl.h
|
||||
+++ components/viz/host/layered_window_updater_impl.h
|
||||
@@ -33,7 +33,7 @@ class VIZ_HOST_EXPORT LayeredWindowUpdaterImpl
|
||||
void OnAllocatedSharedMemory(
|
||||
const gfx::Size& pixel_size,
|
||||
mojo::ScopedSharedBufferHandle scoped_buffer_handle) override;
|
||||
- void Draw(DrawCallback draw_callback) override;
|
||||
+ void Draw(const gfx::Rect& damage_rect, DrawCallback draw_callback) override;
|
||||
|
||||
private:
|
||||
const HWND hwnd_;
|
||||
diff --git components/viz/service/BUILD.gn components/viz/service/BUILD.gn
|
||||
index f17983a5cc70..4a8f2fd8d415 100644
|
||||
--- components/viz/service/BUILD.gn
|
||||
+++ components/viz/service/BUILD.gn
|
||||
@@ -13,6 +13,8 @@ config("viz_service_implementation") {
|
||||
|
||||
viz_component("service") {
|
||||
sources = [
|
||||
+ "//cef/libcef/browser/osr/software_output_device_proxy.cc",
|
||||
+ "//cef/libcef/browser/osr/software_output_device_proxy.h",
|
||||
"display/bsp_tree.cc",
|
||||
"display/bsp_tree.h",
|
||||
"display/bsp_walk_action.cc",
|
||||
diff --git components/viz/service/display_embedder/output_surface_provider_impl.cc components/viz/service/display_embedder/output_surface_provider_impl.cc
|
||||
index 8fe397588eb4..1218985f7310 100644
|
||||
--- components/viz/service/display_embedder/output_surface_provider_impl.cc
|
||||
+++ components/viz/service/display_embedder/output_surface_provider_impl.cc
|
||||
@@ -11,6 +11,7 @@
|
||||
#include "base/compiler_specific.h"
|
||||
#include "base/threading/thread_task_runner_handle.h"
|
||||
#include "cc/base/switches.h"
|
||||
+#include "cef/libcef/browser/osr/software_output_device_proxy.h"
|
||||
#include "components/viz/common/display/renderer_settings.h"
|
||||
#include "components/viz/common/frame_sinks/begin_frame_source.h"
|
||||
#include "components/viz/service/display_embedder/gl_output_surface.h"
|
||||
@@ -243,6 +244,20 @@ OutputSurfaceProviderImpl::CreateSoftwareOutputDeviceForPlatform(
|
||||
if (headless_)
|
||||
return std::make_unique<SoftwareOutputDevice>();
|
||||
|
||||
+ {
|
||||
+ mojo::ScopedAllowSyncCallForTesting allow_sync;
|
||||
+ DCHECK(display_client);
|
||||
+ bool use_proxy_output_device = false;
|
||||
+ if (display_client->UseProxyOutputDevice(&use_proxy_output_device) &&
|
||||
+ use_proxy_output_device) {
|
||||
+ mojom::LayeredWindowUpdaterPtr layered_window_updater;
|
||||
+ display_client->CreateLayeredWindowUpdater(
|
||||
+ mojo::MakeRequest(&layered_window_updater));
|
||||
+ return std::make_unique<SoftwareOutputDeviceProxy>(
|
||||
+ std::move(layered_window_updater));
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
#if defined(OS_WIN)
|
||||
return CreateSoftwareOutputDeviceWin(surface_handle, &output_device_backing_,
|
||||
display_client);
|
||||
diff --git components/viz/service/display_embedder/software_output_device_win.cc components/viz/service/display_embedder/software_output_device_win.cc
|
||||
index 4e3f0255d5fe..0de947b54b7c 100644
|
||||
--- components/viz/service/display_embedder/software_output_device_win.cc
|
||||
+++ components/viz/service/display_embedder/software_output_device_win.cc
|
||||
@@ -268,8 +268,9 @@ void SoftwareOutputDeviceWinProxy::EndPaintDelegated(
|
||||
if (!canvas_)
|
||||
return;
|
||||
|
||||
- layered_window_updater_->Draw(base::BindOnce(
|
||||
- &SoftwareOutputDeviceWinProxy::DrawAck, base::Unretained(this)));
|
||||
+ layered_window_updater_->Draw(
|
||||
+ damage_rect, base::BindOnce(&SoftwareOutputDeviceWinProxy::DrawAck,
|
||||
+ base::Unretained(this)));
|
||||
waiting_on_draw_ack_ = true;
|
||||
|
||||
TRACE_EVENT_ASYNC_BEGIN0("viz", "SoftwareOutputDeviceWinProxy::Draw", this);
|
||||
diff --git mojo/public/cpp/bindings/sync_call_restrictions.h mojo/public/cpp/bindings/sync_call_restrictions.h
|
||||
index 906be544c90f..a110f254d7ec 100644
|
||||
--- mojo/public/cpp/bindings/sync_call_restrictions.h
|
||||
+++ mojo/public/cpp/bindings/sync_call_restrictions.h
|
||||
@@ -34,6 +34,7 @@ class HostContextFactoryPrivate;
|
||||
|
||||
namespace viz {
|
||||
class HostFrameSinkManager;
|
||||
+class GpuDisplayProvider;
|
||||
}
|
||||
|
||||
namespace mojo {
|
||||
@@ -91,6 +92,8 @@ class COMPONENT_EXPORT(MOJO_CPP_BINDINGS) SyncCallRestrictions {
|
||||
// For preventing frame swaps of wrong size during resize on Windows.
|
||||
// (https://crbug.com/811945)
|
||||
friend class ui::HostContextFactoryPrivate;
|
||||
+ // For query of whether to use SoftwareOutputDevice or not
|
||||
+ friend class viz::GpuDisplayProvider;
|
||||
// END ALLOWED USAGE.
|
||||
|
||||
#if ENABLE_SYNC_CALL_RESTRICTIONS
|
||||
diff --git services/viz/privileged/interfaces/compositing/display_private.mojom services/viz/privileged/interfaces/compositing/display_private.mojom
|
||||
index deb327b77054..d9926ec35165 100644
|
||||
--- services/viz/privileged/interfaces/compositing/display_private.mojom
|
||||
+++ services/viz/privileged/interfaces/compositing/display_private.mojom
|
||||
@@ -77,12 +77,14 @@ interface DisplayPrivate {
|
||||
};
|
||||
|
||||
interface DisplayClient {
|
||||
+ [Sync]
|
||||
+ UseProxyOutputDevice() => (bool success);
|
||||
+
|
||||
[EnableIf=is_mac]
|
||||
OnDisplayReceivedCALayerParams(gfx.mojom.CALayerParams ca_layer_params);
|
||||
|
||||
// Creates a LayeredWindowUpdater implementation to draw into a layered
|
||||
// window.
|
||||
- [EnableIf=is_win]
|
||||
CreateLayeredWindowUpdater(LayeredWindowUpdater& layered_window_updater);
|
||||
|
||||
// Notifies that a swap has occurred and provides information about the pixel
|
||||
diff --git services/viz/privileged/interfaces/compositing/layered_window_updater.mojom services/viz/privileged/interfaces/compositing/layered_window_updater.mojom
|
||||
index 360cab3eee4c..6834242f23d2 100644
|
||||
--- services/viz/privileged/interfaces/compositing/layered_window_updater.mojom
|
||||
+++ services/viz/privileged/interfaces/compositing/layered_window_updater.mojom
|
||||
@@ -22,5 +22,5 @@ interface LayeredWindowUpdater {
|
||||
// Draws to the HWND by copying pixels from shared memory. Callback must be
|
||||
// called after draw operation is complete to signal shared memory can be
|
||||
// modified.
|
||||
- Draw() => ();
|
||||
+ Draw(gfx.mojom.Rect damage_rect) => ();
|
||||
};
|
||||
diff --git ui/compositor/compositor.h ui/compositor/compositor.h
|
||||
index 494241c374b7..1cbfb9cdb683 100644
|
||||
--- ui/compositor/compositor.h
|
||||
+++ ui/compositor/compositor.h
|
||||
@@ -23,7 +23,9 @@
|
||||
#include "cc/trees/layer_tree_host_single_thread_client.h"
|
||||
#include "components/viz/common/frame_sinks/begin_frame_args.h"
|
||||
#include "components/viz/common/surfaces/frame_sink_id.h"
|
||||
+#include "components/viz/host/host_display_client.h"
|
||||
#include "components/viz/host/host_frame_sink_client.h"
|
||||
+#include "components/viz/service/display/software_output_device.h"
|
||||
#include "services/viz/privileged/interfaces/compositing/vsync_parameter_observer.mojom-forward.h"
|
||||
#include "third_party/skia/include/core/SkColor.h"
|
||||
#include "third_party/skia/include/core/SkMatrix44.h"
|
||||
@@ -199,6 +201,14 @@ class COMPOSITOR_EXPORT ContextFactory {
|
||||
virtual bool SyncTokensRequiredForDisplayCompositor() = 0;
|
||||
};
|
||||
|
||||
+class COMPOSITOR_EXPORT CompositorDelegate {
|
||||
+ public:
|
||||
+ virtual std::unique_ptr<viz::HostDisplayClient> CreateHostDisplayClient() = 0;
|
||||
+
|
||||
+ protected:
|
||||
+ virtual ~CompositorDelegate() {}
|
||||
+};
|
||||
+
|
||||
// Compositor object to take care of GPU painting.
|
||||
// A Browser compositor object is responsible for generating the final
|
||||
// displayable form of pixels comprising a single widget's contents. It draws an
|
||||
@@ -238,6 +248,9 @@ class COMPOSITOR_EXPORT Compositor : public cc::LayerTreeHostClient,
|
||||
// Schedules a redraw of the layer tree associated with this compositor.
|
||||
void ScheduleDraw();
|
||||
|
||||
+ CompositorDelegate* delegate() const { return delegate_; }
|
||||
+ void SetDelegate(CompositorDelegate* delegate) { delegate_ = delegate; }
|
||||
+
|
||||
// Sets the root of the layer tree drawn by this Compositor. The root layer
|
||||
// must have no parent. The compositor's root layer is reset if the root layer
|
||||
// is destroyed. NULL can be passed to reset the root layer, in which case the
|
||||
@@ -454,6 +467,8 @@ class COMPOSITOR_EXPORT Compositor : public cc::LayerTreeHostClient,
|
||||
ui::ContextFactory* context_factory_;
|
||||
ui::ContextFactoryPrivate* context_factory_private_;
|
||||
|
||||
+ CompositorDelegate* delegate_ = nullptr;
|
||||
+
|
||||
// The root of the Layer tree drawn by this compositor.
|
||||
Layer* root_layer_ = nullptr;
|
||||
|
||||
diff --git ui/compositor/host/host_context_factory_private.cc ui/compositor/host/host_context_factory_private.cc
|
||||
index 0ff1e05244e0..5b8721034296 100644
|
||||
--- ui/compositor/host/host_context_factory_private.cc
|
||||
+++ ui/compositor/host/host_context_factory_private.cc
|
||||
@@ -99,8 +99,13 @@ void HostContextFactoryPrivate::ConfigureCompositor(
|
||||
mojo::MakeRequest(&root_params->compositor_frame_sink_client);
|
||||
root_params->display_private =
|
||||
mojo::MakeRequest(&compositor_data.display_private);
|
||||
- compositor_data.display_client =
|
||||
- std::make_unique<HostDisplayClient>(compositor);
|
||||
+ if (compositor->delegate()) {
|
||||
+ compositor_data.display_client =
|
||||
+ compositor->delegate()->CreateHostDisplayClient();
|
||||
+ } else {
|
||||
+ compositor_data.display_client =
|
||||
+ std::make_unique<HostDisplayClient>(compositor);
|
||||
+ }
|
||||
root_params->display_client =
|
||||
compositor_data.display_client->GetBoundPtr(resize_task_runner_)
|
||||
.PassInterface();
|
|
@ -36,11 +36,11 @@ const int kOsrHeight = 400;
|
|||
|
||||
// bounding client rects for edit box and navigate button
|
||||
#if defined(OS_WIN)
|
||||
const CefRect kExpandedSelectRect(463, 42, 81, 334);
|
||||
const CefRect kExpandedSelectRect(462, 42, 81, 334);
|
||||
#elif defined(OS_MACOSX)
|
||||
const CefRect kExpandedSelectRect(463, 42, 75, 286);
|
||||
const CefRect kExpandedSelectRect(462, 42, 75, 286);
|
||||
#elif defined(OS_LINUX)
|
||||
const CefRect kExpandedSelectRect(463, 42, 79, 334);
|
||||
const CefRect kExpandedSelectRect(462, 42, 79, 334);
|
||||
#else
|
||||
#error "Unsupported platform"
|
||||
#endif // defined(OS_WIN)
|
||||
|
|
Loading…
Reference in New Issue