Bug 1595787: Move ExternalImageHandler and OutputImageHandler traits to webrender_api. r=kvark
authorJosh Matthews <josh@joshmatthews.net>
Thu, 14 Nov 2019 17:40:28 +0000
changeset 502008 24b134b55c5f70eab758d74682fc1f6ca829e0ff
parent 502007 eb83c702dd4f197ab67ae3f78968e86317338773
child 502009 776f4bc4d6113d1b6e301761f3c77fe33fb8df25
push id114172
push userdluca@mozilla.com
push dateTue, 19 Nov 2019 11:31:10 +0000
treeherdermozilla-inbound@b5c5ba07d3db [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewerskvark
bugs1595787
milestone72.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1595787: Move ExternalImageHandler and OutputImageHandler traits to webrender_api. r=kvark Differential Revision: https://phabricator.services.mozilla.com/D52686
gfx/webrender_bindings/src/bindings.rs
gfx/wr/examples/common/boilerplate.rs
gfx/wr/examples/frame_output.rs
gfx/wr/examples/texture_cache_stress.rs
gfx/wr/examples/yuv.rs
gfx/wr/webrender/src/lib.rs
gfx/wr/webrender/src/renderer.rs
gfx/wr/webrender_api/src/image.rs
gfx/wr/wrench/src/yaml_frame_reader.rs
--- a/gfx/webrender_bindings/src/bindings.rs
+++ b/gfx/webrender_bindings/src/bindings.rs
@@ -21,17 +21,17 @@ use std::ops::Range;
 use std::os::raw::{c_void, c_char, c_float};
 #[cfg(target_os = "android")]
 use std::os::raw::{c_int};
 use std::time::Duration;
 use gleam::gl;
 
 use webrender::{
     api::*, api::units::*, ApiRecordingReceiver, AsyncPropertySampler, AsyncScreenshotHandle,
-    BinaryRecorder, Compositor, DebugFlags, Device, ExternalImage, ExternalImageHandler, ExternalImageSource,
+    BinaryRecorder, Compositor, DebugFlags, Device,
     NativeSurfaceId, PipelineInfo, ProfilerHooks, RecordedFrameHandle, Renderer, RendererOptions, RendererStats,
     SceneBuilderHooks, ShaderPrecacheFlags, Shaders, ThreadListener, UploadMethod, VertexUsageHint,
     WrShaders, set_profiler_hooks, CompositorConfig, NativeSurfaceInfo
 };
 use thread_profiler::register_thread_with_profiler;
 use moz2d_renderer::Moz2dBlobImageHandler;
 use program_cache::{WrProgramCache, remove_disk_cache};
 use rayon;
--- a/gfx/wr/examples/common/boilerplate.rs
+++ b/gfx/wr/examples/common/boilerplate.rs
@@ -86,18 +86,18 @@ pub trait Example {
         _: &RenderApi,
         _: DocumentId,
     ) -> bool {
         false
     }
     fn get_image_handlers(
         &mut self,
         _gl: &dyn gl::Gl,
-    ) -> (Option<Box<dyn webrender::ExternalImageHandler>>,
-          Option<Box<dyn webrender::OutputImageHandler>>) {
+    ) -> (Option<Box<dyn ExternalImageHandler>>,
+          Option<Box<dyn OutputImageHandler>>) {
         (None, None)
     }
     fn draw_custom(&mut self, _gl: &dyn gl::Gl) {
     }
 }
 
 pub fn main_wrapper<E: Example>(
     example: &mut E,
--- a/gfx/wr/examples/frame_output.rs
+++ b/gfx/wr/examples/frame_output.rs
@@ -38,34 +38,34 @@ struct App {
 struct OutputHandler {
     texture_id: gl::GLuint
 }
 
 struct ExternalHandler {
     texture_id: gl::GLuint
 }
 
-impl webrender::OutputImageHandler for OutputHandler {
+impl OutputImageHandler for OutputHandler {
     fn lock(&mut self, _id: PipelineId) -> Option<(u32, FramebufferIntSize)> {
         Some((self.texture_id, FramebufferIntSize::new(500, 500)))
     }
 
     fn unlock(&mut self, _id: PipelineId) {}
 }
 
-impl webrender::ExternalImageHandler for ExternalHandler {
+impl ExternalImageHandler for ExternalHandler {
     fn lock(
         &mut self,
         _key: ExternalImageId,
         _channel_index: u8,
         _rendering: ImageRendering
-    ) -> webrender::ExternalImage {
-        webrender::ExternalImage {
+    ) -> ExternalImage {
+        ExternalImage {
             uv: TexelRect::new(0.0, 0.0, 1.0, 1.0),
-            source: webrender::ExternalImageSource::NativeTexture(self.texture_id),
+            source: ExternalImageSource::NativeTexture(self.texture_id),
         }
     }
     fn unlock(&mut self, _key: ExternalImageId, _channel_index: u8) {}
 }
 
 impl App {
     fn init_output_document(
         &mut self,
@@ -177,18 +177,18 @@ impl Example for App {
         );
 
         builder.pop_stacking_context();
     }
 
     fn get_image_handlers(
         &mut self,
         gl: &dyn gl::Gl,
-    ) -> (Option<Box<dyn webrender::ExternalImageHandler>>,
-          Option<Box<dyn webrender::OutputImageHandler>>) {
+    ) -> (Option<Box<dyn ExternalImageHandler>>,
+          Option<Box<dyn OutputImageHandler>>) {
         let texture_id = gl.gen_textures(1)[0];
 
         gl.bind_texture(gl::TEXTURE_2D, texture_id);
         gl.tex_parameter_i(
             gl::TEXTURE_2D,
             gl::TEXTURE_MAG_FILTER,
             gl::LINEAR as gl::GLint,
         );
--- a/gfx/wr/examples/texture_cache_stress.rs
+++ b/gfx/wr/examples/texture_cache_stress.rs
@@ -57,27 +57,27 @@ impl ImageGenerator {
         self.next_pattern = (self.next_pattern + 1) % self.patterns.len();
     }
 
     fn take(&mut self) -> Vec<u8> {
         mem::replace(&mut self.current_image, Vec::new())
     }
 }
 
-impl webrender::ExternalImageHandler for ImageGenerator {
+impl ExternalImageHandler for ImageGenerator {
     fn lock(
         &mut self,
         _key: ExternalImageId,
         channel_index: u8,
         _rendering: ImageRendering
-    ) -> webrender::ExternalImage {
+    ) -> ExternalImage {
         self.generate_image(channel_index as i32);
-        webrender::ExternalImage {
+        ExternalImage {
             uv: TexelRect::new(0.0, 0.0, 1.0, 1.0),
-            source: webrender::ExternalImageSource::RawData(&self.current_image),
+            source: ExternalImageSource::RawData(&self.current_image),
         }
     }
     fn unlock(&mut self, _key: ExternalImageId, _channel_index: u8) {}
 }
 
 struct App {
     stress_keys: Vec<ImageKey>,
     image_key: Option<ImageKey>,
@@ -294,18 +294,18 @@ impl Example for App {
         }
 
         false
     }
 
     fn get_image_handlers(
         &mut self,
         _gl: &dyn gl::Gl,
-    ) -> (Option<Box<dyn webrender::ExternalImageHandler>>,
-          Option<Box<dyn webrender::OutputImageHandler>>) {
+    ) -> (Option<Box<dyn ExternalImageHandler>>,
+          Option<Box<dyn OutputImageHandler>>) {
         (Some(Box::new(ImageGenerator::new())), None)
     }
 }
 
 fn main() {
     let mut app = App {
         image_key: None,
         stress_keys: Vec::new(),
--- a/gfx/wr/examples/yuv.rs
+++ b/gfx/wr/examples/yuv.rs
@@ -56,27 +56,27 @@ impl YuvImageProvider {
         init_gl_texture(texture_ids[3], gl::RED, gl::RED, &[127; 100 * 100], gl);
 
         YuvImageProvider {
             texture_ids
         }
     }
 }
 
-impl webrender::ExternalImageHandler for YuvImageProvider {
+impl ExternalImageHandler for YuvImageProvider {
     fn lock(
         &mut self,
         key: ExternalImageId,
         _channel_index: u8,
         _rendering: ImageRendering
-    ) -> webrender::ExternalImage {
+    ) -> ExternalImage {
         let id = self.texture_ids[key.0 as usize];
-        webrender::ExternalImage {
+        ExternalImage {
             uv: TexelRect::new(0.0, 0.0, 1.0, 1.0),
-            source: webrender::ExternalImageSource::NativeTexture(id),
+            source: ExternalImageSource::NativeTexture(id),
         }
     }
     fn unlock(&mut self, _key: ExternalImageId, _channel_index: u8) {
     }
 }
 
 struct App {
     texture_id: gl::GLuint,
@@ -193,18 +193,18 @@ impl Example for App {
         _document_id: DocumentId,
     ) -> bool {
         false
     }
 
     fn get_image_handlers(
         &mut self,
         gl: &dyn gl::Gl,
-    ) -> (Option<Box<dyn webrender::ExternalImageHandler>>,
-          Option<Box<dyn webrender::OutputImageHandler>>) {
+    ) -> (Option<Box<dyn ExternalImageHandler>>,
+          Option<Box<dyn OutputImageHandler>>) {
         let provider = YuvImageProvider::new(gl);
         self.texture_id = provider.texture_ids[0];
         (Some(Box::new(provider)), None)
     }
 
     fn draw_custom(&mut self, gl: &dyn gl::Gl) {
         init_gl_texture(self.texture_id, gl::RED, gl::RED, &[self.current_value; 100 * 100], gl);
         self.current_value = self.current_value.wrapping_add(1);
--- a/gfx/wr/webrender/src/lib.rs
+++ b/gfx/wr/webrender/src/lib.rs
@@ -204,17 +204,17 @@ extern crate webrender_build;
 pub use crate::composite::{CompositorConfig, Compositor, NativeSurfaceId, NativeSurfaceInfo};
 pub use crate::device::{build_shader_strings, UploadMethod, VertexUsageHint, get_gl_target};
 pub use crate::device::{ProgramBinary, ProgramCache, ProgramCacheObserver, FormatDesc};
 pub use crate::device::Device;
 pub use crate::frame_builder::ChasePrimitive;
 pub use crate::prim_store::PrimitiveDebugId;
 pub use crate::profiler::{ProfilerHooks, set_profiler_hooks};
 pub use crate::renderer::{
-    AsyncPropertySampler, CpuProfile, DebugFlags, OutputImageHandler, RendererKind, ExternalImage,
-    ExternalImageHandler, ExternalImageSource, GpuProfile, GraphicsApi, GraphicsApiInfo,
-    PipelineInfo, Renderer, RendererError, RendererOptions, RenderResults, RendererStats, SceneBuilderHooks,
-    ThreadListener, ShaderPrecacheFlags, MAX_VERTEX_TEXTURE_WIDTH,
+    AsyncPropertySampler, CpuProfile, DebugFlags, RendererKind, GpuProfile, GraphicsApi,
+    GraphicsApiInfo, PipelineInfo, Renderer, RendererError, RendererOptions, RenderResults,
+    RendererStats, SceneBuilderHooks, ThreadListener, ShaderPrecacheFlags,
+    MAX_VERTEX_TEXTURE_WIDTH,
 };
 pub use crate::screen_capture::{AsyncScreenshotHandle, RecordedFrameHandle};
 pub use crate::shade::{Shaders, WrShaders};
 pub use api as webrender_api;
 pub use webrender_build::shader::ProgramSourceDigest;
--- a/gfx/wr/webrender/src/renderer.rs
+++ b/gfx/wr/webrender/src/renderer.rs
@@ -30,21 +30,23 @@
 //! the content rectangle to -1 to 1
 //!   - the viewport transformation is setup to map the whole range to
 //! the framebuffer rectangle provided by the document view, stored in `DrawTarget`
 //!   - all the direct framebuffer operations, like blitting, reading pixels, and setting
 //! up the scissor, are accepting already transformed coordinates, which we can get by
 //! calling `DrawTarget::to_framebuffer_rect`
 
 use api::{ApiMsg, BlobImageHandler, ColorF, ColorU, MixBlendMode};
-use api::{DocumentId, Epoch, ExternalImageId};
-use api::{ExternalImageType, FontRenderMode, FrameMsg, ImageFormat, PipelineId};
-use api::{ImageRendering, Checkpoint, NotificationRequest};
+use api::{DocumentId, Epoch, ExternalImageHandler, ExternalImageId};
+use api::{ExternalImageSource, ExternalImageType, FontRenderMode, FrameMsg, ImageFormat};
+use api::{PipelineId, ImageRendering, Checkpoint, NotificationRequest, OutputImageHandler};
 use api::{DebugCommand, MemoryReport, VoidPtrToSizeFn};
 use api::{RenderApiSender, RenderNotifier, TextureTarget};
+#[cfg(feature = "replay")]
+use api::ExternalImage;
 use api::channel;
 use api::units::*;
 pub use api::DebugFlags;
 use api::channel::{MsgSender, PayloadReceiverHelperMethods};
 use crate::batch::{AlphaBatchContainer, BatchKind, BatchFeatures, BatchTextures, BrushBatchKind, ClipBatchList};
 #[cfg(any(feature = "capture", feature = "replay"))]
 use crate::capture::{CaptureConfig, ExternalCaptureImage, PlainExternalImage};
 use crate::composite::{CompositeState, CompositeTileSurface, CompositeTile, CompositorKind, Compositor};
@@ -5987,62 +5989,16 @@ impl Renderer {
                 i as usize,
                 false,
             ));
             self.device.clear_target(Some(color), None, None);
         }
     }
 }
 
-pub enum ExternalImageSource<'a> {
-    RawData(&'a [u8]),  // raw buffers.
-    NativeTexture(u32), // It's a gl::GLuint texture handle
-    Invalid,
-}
-
-/// The data that an external client should provide about
-/// an external image. The timestamp is used to test if
-/// the renderer should upload new texture data this
-/// frame. For instance, if providing video frames, the
-/// application could call wr.render() whenever a new
-/// video frame is ready. If the callback increments
-/// the returned timestamp for a given image, the renderer
-/// will know to re-upload the image data to the GPU.
-/// Note that the UV coords are supplied in texel-space!
-pub struct ExternalImage<'a> {
-    pub uv: TexelRect,
-    pub source: ExternalImageSource<'a>,
-}
-
-/// The interfaces that an application can implement to support providing
-/// external image buffers.
-/// When the application passes an external image to WR, it should keep that
-/// external image life time. People could check the epoch id in RenderNotifier
-/// at the client side to make sure that the external image is not used by WR.
-/// Then, do the clean up for that external image.
-pub trait ExternalImageHandler {
-    /// Lock the external image. Then, WR could start to read the image content.
-    /// The WR client should not change the image content until the unlock()
-    /// call. Provide ImageRendering for NativeTexture external images.
-    fn lock(&mut self, key: ExternalImageId, channel_index: u8, rendering: ImageRendering) -> ExternalImage;
-    /// Unlock the external image. The WR should not read the image content
-    /// after this call.
-    fn unlock(&mut self, key: ExternalImageId, channel_index: u8);
-}
-
-/// Allows callers to receive a texture with the contents of a specific
-/// pipeline copied to it. Lock should return the native texture handle
-/// and the size of the texture. Unlock will only be called if the lock()
-/// call succeeds, when WR has issued the GL commands to copy the output
-/// to the texture handle.
-pub trait OutputImageHandler {
-    fn lock(&mut self, pipeline_id: PipelineId) -> Option<(u32, FramebufferIntSize)>;
-    fn unlock(&mut self, pipeline_id: PipelineId);
-}
-
 pub trait ThreadListener {
     fn thread_started(&self, thread_name: &str);
     fn thread_stopped(&self, thread_name: &str);
 }
 
 /// Allows callers to hook in at certain points of the async scene build. These
 /// functions are all called from the scene builder thread.
 pub trait SceneBuilderHooks {
@@ -6342,17 +6298,20 @@ impl ExternalImageHandler for DummyExter
                 CapturedExternalImageData::Buffer(ref arc) => ExternalImageSource::RawData(&*arc),
             }
         }
     }
     fn unlock(&mut self, _key: ExternalImageId, _channel_index: u8) {}
 }
 
 #[cfg(feature = "replay")]
-impl OutputImageHandler for () {
+struct VoidHandler;
+
+#[cfg(feature = "replay")]
+impl OutputImageHandler for VoidHandler {
     fn lock(&mut self, _: PipelineId) -> Option<(u32, FramebufferIntSize)> {
         None
     }
     fn unlock(&mut self, _: PipelineId) {
         unreachable!()
     }
 }
 
@@ -6705,17 +6664,17 @@ impl Renderer {
 
                 let value = (CapturedExternalImageData::NativeTexture(tid), plain_ext.uv);
                 image_handler.data.insert(key, value);
             }
 
             self.device.end_frame();
         }
 
-        self.output_image_handler = Some(Box::new(()) as Box<_>);
+        self.output_image_handler = Some(Box::new(VoidHandler) as Box<_>);
         self.external_image_handler = Some(Box::new(image_handler) as Box<_>);
         info!("done.");
     }
 }
 
 fn get_vao<'a>(vertex_array_kind: VertexArrayKind,
                vaos: &'a RendererVAOs)
                -> &'a VAO {
--- a/gfx/wr/webrender_api/src/image.rs
+++ b/gfx/wr/webrender_api/src/image.rs
@@ -4,17 +4,18 @@
 
 #![deny(missing_docs)]
 
 use euclid::{size2, Rect, num::Zero};
 use peek_poke::PeekPoke;
 use std::ops::{Add, Sub};
 use std::sync::Arc;
 // local imports
-use crate::api::{IdNamespace, TileSize};
+use crate::api::{IdNamespace, PipelineId, TileSize};
+use crate::display_item::ImageRendering;
 use crate::font::{FontInstanceKey, FontInstanceData, FontKey, FontTemplate};
 use crate::units::*;
 
 /// An opaque identifier describing an image registered with WebRender.
 /// This is used as a handle to reference images, and is used as the
 /// hash map key for the actual image storage in the `ResourceCache`.
 #[repr(C)]
 #[derive(Clone, Copy, Debug, Deserialize, Eq, Hash, MallocSizeOf, PartialEq, Serialize, PeekPoke)]
@@ -52,16 +53,64 @@ impl BlobImageKey {
 
 /// An arbitrary identifier for an external image provided by the
 /// application. It must be a unique identifier for each external
 /// image.
 #[repr(C)]
 #[derive(Copy, Clone, Debug, Eq, PartialEq, Hash, Serialize, Deserialize)]
 pub struct ExternalImageId(pub u64);
 
+/// The source for an external image.
+pub enum ExternalImageSource<'a> {
+    /// A raw pixel buffer.
+    RawData(&'a [u8]),
+    /// A gl::GLuint texture handle.
+    NativeTexture(u32),
+    /// An invalid source.
+    Invalid,
+}
+
+/// The data that an external client should provide about
+/// an external image. For instance, if providing video frames,
+/// the application could call wr.render() whenever a new
+/// video frame is ready. Note that the UV coords are supplied
+/// in texel-space!
+pub struct ExternalImage<'a> {
+    /// UV coordinates for the image.
+    pub uv: TexelRect,
+    /// The source for this image's contents.
+    pub source: ExternalImageSource<'a>,
+}
+
+/// The interfaces that an application can implement to support providing
+/// external image buffers.
+/// When the application passes an external image to WR, it should keep that
+/// external image life time. People could check the epoch id in RenderNotifier
+/// at the client side to make sure that the external image is not used by WR.
+/// Then, do the clean up for that external image.
+pub trait ExternalImageHandler {
+    /// Lock the external image. Then, WR could start to read the image content.
+    /// The WR client should not change the image content until the unlock()
+    /// call. Provide ImageRendering for NativeTexture external images.
+    fn lock(&mut self, key: ExternalImageId, channel_index: u8, rendering: ImageRendering) -> ExternalImage;
+    /// Unlock the external image. WR should not read the image content
+    /// after this call.
+    fn unlock(&mut self, key: ExternalImageId, channel_index: u8);
+}
+
+/// Allows callers to receive a texture with the contents of a specific
+/// pipeline copied to it.
+pub trait OutputImageHandler {
+    /// Return the native texture handle and the size of the texture.
+    fn lock(&mut self, pipeline_id: PipelineId) -> Option<(u32, FramebufferIntSize)>;
+    /// Unlock will only be called if the lock() call succeeds, when WR has issued
+    /// the GL commands to copy the output to the texture handle.
+    fn unlock(&mut self, pipeline_id: PipelineId);
+}
+
 /// Specifies the type of texture target in driver terms.
 #[repr(u8)]
 #[derive(Copy, Clone, Debug, Eq, Hash, PartialEq, Serialize, Deserialize)]
 pub enum TextureTarget {
     /// Standard texture. This maps to GL_TEXTURE_2D in OpenGL.
     Default = 0,
     /// Array texture. This maps to GL_TEXTURE_2D_ARRAY in OpenGL. See
     /// https://www.khronos.org/opengl/wiki/Array_Texture for background
--- a/gfx/wr/wrench/src/yaml_frame_reader.rs
+++ b/gfx/wr/wrench/src/yaml_frame_reader.rs
@@ -133,27 +133,27 @@ impl LocalExternalImageHandler {
                 id: image_id,
                 channel_index: channel_idx,
                 image_type: ExternalImageType::TextureHandle(target)
             }
         )
     }
 }
 
-impl webrender::ExternalImageHandler for LocalExternalImageHandler {
+impl ExternalImageHandler for LocalExternalImageHandler {
     fn lock(
         &mut self,
         key: ExternalImageId,
         _channel_index: u8,
         _rendering: ImageRendering,
-    ) -> webrender::ExternalImage {
+    ) -> ExternalImage {
         let (id, desc) = self.texture_ids[key.0 as usize];
-        webrender::ExternalImage {
+        ExternalImage {
             uv: TexelRect::new(0.0, 0.0, desc.size.width as f32, desc.size.height as f32),
-            source: webrender::ExternalImageSource::NativeTexture(id),
+            source: ExternalImageSource::NativeTexture(id),
         }
     }
     fn unlock(&mut self, _key: ExternalImageId, _channel_index: u8) {}
 }
 
 fn broadcast<T: Clone>(base_vals: &[T], num_items: usize) -> Vec<T> {
     if base_vals.len() == num_items {
         return base_vals.to_vec();