From b637815c6df237f09e3f0b6a5c0b93924a2a1291 Mon Sep 17 00:00:00 2001 From: Nicolas Silva Date: Tue, 17 Jan 2017 14:46:31 -0500 Subject: [PATCH] Bug 1328602 - Implement forwarding events to the render thread through the render backend. r=gfx? --- gfx/webrender_bindings/RenderThread.cpp | 8 ++++---- gfx/webrender_bindings/WebRenderAPI.cpp | 20 ++++++++++++-------- gfx/webrender_bindings/WebRenderAPI.h | 3 +++ gfx/webrender_bindings/src/bindings.rs | 17 +++++++++++++++-- gfx/webrender_bindings/webrender_ffi.h | 3 +++ 5 files changed, 37 insertions(+), 14 deletions(-) diff --git a/gfx/webrender_bindings/RenderThread.cpp b/gfx/webrender_bindings/RenderThread.cpp index 91148ae1b6d8..a776477f0d21 100644 --- a/gfx/webrender_bindings/RenderThread.cpp +++ b/gfx/webrender_bindings/RenderThread.cpp @@ -191,18 +191,18 @@ RenderThread::UpdateAndRender(wr::WindowId aWindowId) extern "C" { -void wr_notifier_new_frame_ready(uint64_t aWindowId) +void wr_notifier_new_frame_ready(WrWindowId aWindowId) { mozilla::wr::RenderThread::Get()->NewFrameReady(mozilla::wr::WindowId(aWindowId)); } -void wr_notifier_new_scroll_frame_ready(uint64_t aWindowId, bool aCompositeNeeded) +void wr_notifier_new_scroll_frame_ready(WrWindowId aWindowId, bool aCompositeNeeded) { mozilla::wr::RenderThread::Get()->NewScrollFrameReady(mozilla::wr::WindowId(aWindowId), aCompositeNeeded); } -void wr_notifier_pipeline_size_changed(uint64_t aWindowId, +void wr_notifier_pipeline_size_changed(WrWindowId aWindowId, uint64_t aPipelineId, float aWidth, float aHeight) @@ -211,7 +211,7 @@ void wr_notifier_pipeline_size_changed(uint64_t aWindowId, aPipelineId, aWidth, aHeight); } -void wr_notifier_external_event(uint64_t aWindowId, size_t aRawEvent) +void wr_notifier_external_event(WrWindowId aWindowId, size_t aRawEvent) { mozilla::UniquePtr evt( reinterpret_cast(aRawEvent)); diff --git a/gfx/webrender_bindings/WebRenderAPI.cpp b/gfx/webrender_bindings/WebRenderAPI.cpp index 1c6dff1a8b3b..04971702b09e 100644 --- a/gfx/webrender_bindings/WebRenderAPI.cpp +++ b/gfx/webrender_bindings/WebRenderAPI.cpp @@ -146,6 +146,10 @@ WebRenderAPI::Create(bool aEnableProfiler, WebRenderAPI::~WebRenderAPI() { + layers::SynchronousTask task("Destroy WebRenderAPI"); + auto event = MakeUnique(&task); + RunOnRenderThread(Move(event)); + task.Wait(); #ifdef MOZ_ENABLE_WEBRENDER // Need to wrap this in an ifdef otherwise VC++ emits a warning (treated as error) @@ -154,13 +158,6 @@ WebRenderAPI::~WebRenderAPI() // MOZ_MAKE_COMPILER_ASSUME_IS_UNREACHABLE annotations in webrender.h wr_api_delete(mWRApi); #endif - - layers::SynchronousTask task("Destroy WebRenderAPI"); - auto event = MakeUnique(&task); - // TODO use the WebRender API instead of scheduling on this message loop directly. - // this needs PR #688 - RenderThread::Get()->RunEvent(mId, Move(event)); - task.Wait(); } void @@ -256,7 +253,14 @@ void WebRenderAPI::SetProfilerEnabled(bool aEnabled) { auto event = MakeUnique(aEnabled); - RenderThread::Get()->RunEvent(mId, Move(event)); + RunOnRenderThread(Move(event)); +} + +void +WebRenderAPI::RunOnRenderThread(UniquePtr&& aEvent) +{ + auto event = reinterpret_cast(aEvent.release()); + wr_api_send_external_event(mWRApi, event); } DisplayListBuilder::DisplayListBuilder(const LayerIntSize& aSize, PipelineId aId) diff --git a/gfx/webrender_bindings/WebRenderAPI.h b/gfx/webrender_bindings/WebRenderAPI.h index 5be7a9465889..bd7fed923efb 100644 --- a/gfx/webrender_bindings/WebRenderAPI.h +++ b/gfx/webrender_bindings/WebRenderAPI.h @@ -28,6 +28,7 @@ namespace wr { class DisplayListBuilder; class RendererOGL; class NewRenderer; +class RendererEvent; class WebRenderAPI { @@ -69,6 +70,8 @@ public: void SetProfilerEnabled(bool aEnabled); + void RunOnRenderThread(UniquePtr&& aEvent); + protected: WebRenderAPI(WrAPI* aRawApi, wr::WindowId aId) : mWRApi(aRawApi) diff --git a/gfx/webrender_bindings/src/bindings.rs b/gfx/webrender_bindings/src/bindings.rs index 6c2947cfdcb0..77161ba9fdd0 100644 --- a/gfx/webrender_bindings/src/bindings.rs +++ b/gfx/webrender_bindings/src/bindings.rs @@ -10,7 +10,7 @@ use webrender_traits::{PipelineId, ClipRegion}; use webrender_traits::{Epoch, ColorF, GlyphInstance}; use webrender_traits::{ImageData, ImageFormat, ImageKey, ImageMask, ImageRendering, RendererKind}; use webrender_traits::{ExternalImageId, RenderApi, FontKey}; -use webrender_traits::{DeviceUintSize}; +use webrender_traits::{DeviceUintSize, ExternalEvent}; use webrender_traits::{LayoutPoint, LayoutRect, LayoutSize, LayoutTransform}; use webrender::renderer::{Renderer, RendererOptions}; use webrender::renderer::{ExternalImage, ExternalImageHandler, ExternalImageSource}; @@ -234,7 +234,6 @@ extern { fn wr_notifier_new_frame_ready(window_id: u64); fn wr_notifier_new_scroll_frame_ready(window_id: u64, composite_needed: bool); fn wr_notifier_pipeline_size_changed(window_id: u64, pipeline: u64, new_width: f32, new_height: f32); - // TODO: Waiting for PR #688 fn wr_notifier_external_event(window_id: u64, raw_event: usize); } @@ -264,6 +263,12 @@ impl webrender_traits::RenderNotifier for CppNotifier { wr_notifier_pipeline_size_changed(self.window_id, id, w, h); } } + + fn external_event(&mut self, event: ExternalEvent) { + unsafe { + wr_notifier_external_event(self.window_id, event.unwrap()); + } + } } // RenderThread WIP notes: @@ -649,6 +654,14 @@ pub extern fn wr_api_delete_image(api: &mut RenderApi, key: ImageKey) { api.delete_image(key) } +#[no_mangle] +pub extern fn wr_api_send_external_event(api: &mut RenderApi, evt: usize) { + assert!(unsafe { is_in_compositor_thread() }); + + api.send_external_event(ExternalEvent::from_raw(evt)); +} + + #[no_mangle] pub extern fn wr_dp_push_rect(state: &mut WrState, rect: WrRect, clip: WrRect, r: f32, g: f32, b: f32, a: f32) { assert!( unsafe { is_in_compositor_thread() }); diff --git a/gfx/webrender_bindings/webrender_ffi.h b/gfx/webrender_bindings/webrender_ffi.h index 2bd3040b5664..b40882699cea 100644 --- a/gfx/webrender_bindings/webrender_ffi.h +++ b/gfx/webrender_bindings/webrender_ffi.h @@ -245,6 +245,9 @@ wr_api_set_root_pipeline(WrAPI* api, WrPipelineId pipeline_id) WR_FUNC; WR_INLINE void wr_api_set_root_display_list(WrAPI* api, WrState* state, uint32_t epoch, float w, float h) WR_FUNC; +WR_INLINE void +wr_api_send_external_event(WrAPI* api, uintptr_t evt) WR_FUNC; + WR_INLINE void wr_window_init_pipeline_epoch(WrWindowState* window, WrPipelineId pipeline, uint32_t width, uint32_t height) WR_FUNC;