diff --git a/Cargo.lock b/Cargo.lock index 11de75281e7..8b3dbf3754b 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -781,6 +781,7 @@ dependencies = [ "bitflags 2.9.0", "byteorder", "canvas_traits", + "compositing_traits", "crossbeam-channel", "cssparser", "euclid", @@ -803,7 +804,6 @@ dependencies = [ "unicode-script", "webrender", "webrender_api", - "webrender_traits", "webxr", "webxr-api", ] @@ -1106,7 +1106,6 @@ dependencies = [ "tracing", "webrender", "webrender_api", - "webrender_traits", "webxr", ] @@ -1116,16 +1115,23 @@ version = "0.0.1" dependencies = [ "base", "crossbeam-channel", + "dpi", "embedder_traits", "euclid", + "gleam", + "glow", + "image", "ipc-channel", "log", "pixels", - "script_traits", + "raw-window-handle", + "serde", + "servo_geometry", "strum_macros", + "stylo", "stylo_traits", + "surfman", "webrender_api", - "webrender_traits", ] [[package]] @@ -1176,7 +1182,6 @@ dependencies = [ "webgpu_traits", "webrender", "webrender_api", - "webrender_traits", "webxr-api", ] @@ -2196,6 +2201,7 @@ dependencies = [ "base", "bitflags 2.9.0", "byteorder", + "compositing_traits", "core-foundation 0.9.4", "core-graphics", "core-text", @@ -2231,7 +2237,6 @@ dependencies = [ "unicode-script", "url", "webrender_api", - "webrender_traits", "xml-rs", "yeslogic-fontconfig-sys", ] @@ -4185,6 +4190,7 @@ dependencies = [ "base", "bitflags 2.9.0", "canvas_traits", + "compositing_traits", "data-url", "embedder_traits", "euclid", @@ -4218,7 +4224,6 @@ dependencies = [ "unicode-script", "url", "webrender_api", - "webrender_traits", "xi-unicode", ] @@ -4228,6 +4233,7 @@ version = "0.0.1" dependencies = [ "app_units", "base", + "compositing_traits", "constellation_traits", "embedder_traits", "euclid", @@ -4256,7 +4262,6 @@ dependencies = [ "tracing", "url", "webrender_api", - "webrender_traits", ] [[package]] @@ -4408,7 +4413,6 @@ dependencies = [ "webgpu", "webrender", "webrender_api", - "webrender_traits", "webxr", "webxr-api", "winit", @@ -4568,6 +4572,7 @@ checksum = "2532096657941c2fea9c289d370a250971c689d4f143798ff67113ec042024a5" name = "media" version = "0.0.1" dependencies = [ + "compositing_traits", "euclid", "fnv", "ipc-channel", @@ -4576,7 +4581,6 @@ dependencies = [ "servo-media", "servo_config", "webrender_api", - "webrender_traits", ] [[package]] @@ -4869,6 +4873,7 @@ dependencies = [ "base64 0.22.1", "bytes", "chrono", + "compositing_traits", "content-security-policy", "cookie 0.18.1", "crossbeam-channel", @@ -4919,7 +4924,6 @@ dependencies = [ "uuid", "webpki-roots", "webrender_api", - "webrender_traits", ] [[package]] @@ -4927,6 +4931,7 @@ name = "net_traits" version = "0.0.1" dependencies = [ "base", + "compositing_traits", "content-security-policy", "cookie 0.18.1", "crossbeam-channel", @@ -4950,7 +4955,6 @@ dependencies = [ "servo_url", "url", "uuid", - "webrender_traits", ] [[package]] @@ -6307,6 +6311,7 @@ dependencies = [ "cbc", "chrono", "cipher", + "compositing_traits", "constellation_traits", "content-security-policy", "cookie 0.18.1", @@ -6393,7 +6398,6 @@ dependencies = [ "webdriver", "webgpu_traits", "webrender_api", - "webrender_traits", "webxr-api", "wgpu-core", "wgpu-types", @@ -6445,6 +6449,7 @@ dependencies = [ "atomic_refcell", "base", "canvas_traits", + "compositing_traits", "constellation_traits", "embedder_traits", "euclid", @@ -6470,7 +6475,6 @@ dependencies = [ "stylo", "stylo_traits", "webrender_api", - "webrender_traits", ] [[package]] @@ -6491,6 +6495,7 @@ dependencies = [ "base", "bluetooth_traits", "canvas_traits", + "compositing_traits", "constellation_traits", "crossbeam-channel", "devtools_traits", @@ -6513,7 +6518,6 @@ dependencies = [ "stylo_traits", "webgpu_traits", "webrender_api", - "webrender_traits", "webxr-api", ] @@ -8571,6 +8575,7 @@ version = "0.0.1" dependencies = [ "arrayvec", "base", + "compositing_traits", "euclid", "ipc-channel", "log", @@ -8580,7 +8585,6 @@ dependencies = [ "webgpu_traits", "webrender", "webrender_api", - "webrender_traits", "wgpu-core", "wgpu-types", ] @@ -8673,29 +8677,6 @@ dependencies = [ "lazy_static", ] -[[package]] -name = "webrender_traits" -version = "0.0.1" -dependencies = [ - "base", - "dpi", - "embedder_traits", - "euclid", - "gleam", - "glow", - "image", - "ipc-channel", - "libc", - "log", - "raw-window-handle", - "serde", - "servo-media", - "servo_geometry", - "stylo", - "surfman", - "webrender_api", -] - [[package]] name = "webxr" version = "0.0.1" diff --git a/Cargo.toml b/Cargo.toml index 413a41c2e08..0f0b4420c5f 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -166,7 +166,6 @@ webgpu_traits = { path = "components/shared/webgpu" } webpki-roots = "0.26" webrender = { git = "https://github.com/servo/webrender", branch = "0.66", features = ["capture"] } webrender_api = { git = "https://github.com/servo/webrender", branch = "0.66" } -webrender_traits = { path = "components/shared/webrender" } webxr-api = { path = "components/shared/webxr" } wgpu-core = { git = "https://github.com/gfx-rs/wgpu", rev = "2f255edc60e9669c8c737464c59af10d59a31126" } wgpu-types = { git = "https://github.com/gfx-rs/wgpu", rev = "2f255edc60e9669c8c737464c59af10d59a31126" } diff --git a/components/canvas/Cargo.toml b/components/canvas/Cargo.toml index 10ac5a35cd4..a9c06784d18 100644 --- a/components/canvas/Cargo.toml +++ b/components/canvas/Cargo.toml @@ -20,6 +20,7 @@ app_units = { workspace = true } bitflags = { workspace = true } byteorder = { workspace = true } canvas_traits = { workspace = true } +compositing_traits = { workspace = true } crossbeam-channel = { workspace = true } cssparser = { workspace = true } euclid = { workspace = true } @@ -42,6 +43,5 @@ surfman = { workspace = true } unicode-script = { workspace = true } webrender = { workspace = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } webxr = { path = "../webxr", features = ["ipc"], optional = true } webxr-api = { workspace = true, features = ["ipc"], optional = true } diff --git a/components/canvas/canvas_data.rs b/components/canvas/canvas_data.rs index 34942388c23..d6e35b2cbaf 100644 --- a/components/canvas/canvas_data.rs +++ b/components/canvas/canvas_data.rs @@ -7,6 +7,7 @@ use std::sync::Arc; use app_units::Au; use canvas_traits::canvas::*; +use compositing_traits::{CrossProcessCompositorApi, ImageUpdate, SerializableImageData}; use euclid::default::{Box2D, Point2D, Rect, Size2D, Transform2D, Vector2D}; use euclid::point2; use fonts::{ @@ -23,7 +24,6 @@ use style::properties::style_structs::Font as FontStyleStruct; use unicode_script::Script; use webrender_api::units::RectExt as RectExt_; use webrender_api::{ImageDescriptor, ImageDescriptorFlags, ImageFormat, ImageKey}; -use webrender_traits::{CrossProcessCompositorApi, ImageUpdate, SerializableImageData}; use crate::raqote_backend::Repetition; diff --git a/components/canvas/canvas_paint_thread.rs b/components/canvas/canvas_paint_thread.rs index 1c6877772d3..8b1b5038334 100644 --- a/components/canvas/canvas_paint_thread.rs +++ b/components/canvas/canvas_paint_thread.rs @@ -9,6 +9,7 @@ use std::thread; use canvas_traits::ConstellationCanvasMsg; use canvas_traits::canvas::*; +use compositing_traits::CrossProcessCompositorApi; use crossbeam_channel::{Sender, select, unbounded}; use euclid::default::Size2D; use fonts::{FontContext, SystemFontServiceProxy}; @@ -17,7 +18,6 @@ use ipc_channel::router::ROUTER; use log::warn; use net_traits::ResourceThreads; use webrender_api::ImageKey; -use webrender_traits::CrossProcessCompositorApi; use crate::canvas_data::*; diff --git a/components/canvas/webgl_mode/inprocess.rs b/components/canvas/webgl_mode/inprocess.rs index 5a7e59ebaad..566da2c58c8 100644 --- a/components/canvas/webgl_mode/inprocess.rs +++ b/components/canvas/webgl_mode/inprocess.rs @@ -7,6 +7,10 @@ use std::rc::Rc; use std::sync::{Arc, Mutex}; use canvas_traits::webgl::{GlType, WebGLContextId, WebGLMsg, WebGLThreads, webgl_channel}; +use compositing_traits::rendering_context::RenderingContext; +use compositing_traits::{ + WebrenderExternalImageApi, WebrenderExternalImageRegistry, WebrenderImageSource, +}; use euclid::default::Size2D; use fnv::FnvHashMap; use log::debug; @@ -14,10 +18,6 @@ use surfman::chains::{SwapChainAPI, SwapChains, SwapChainsAPI}; use surfman::{Device, SurfaceTexture}; use webrender::RenderApiSender; use webrender_api::DocumentId; -use webrender_traits::rendering_context::RenderingContext; -use webrender_traits::{ - WebrenderExternalImageApi, WebrenderExternalImageRegistry, WebrenderImageSource, -}; #[cfg(feature = "webxr")] use webxr::SurfmanGL as WebXRSurfman; #[cfg(feature = "webxr")] diff --git a/components/canvas/webgl_thread.rs b/components/canvas/webgl_thread.rs index aee5663c2a7..e3f0c77b4b3 100644 --- a/components/canvas/webgl_thread.rs +++ b/components/canvas/webgl_thread.rs @@ -22,6 +22,7 @@ use canvas_traits::webgl::{ WebGLSLVersion, WebGLSamplerId, WebGLSender, WebGLShaderId, WebGLSyncId, WebGLTextureId, WebGLVersion, WebGLVertexArrayId, YAxisTreatment, }; +use compositing_traits::{WebrenderExternalImageRegistry, WebrenderImageHandlerType}; use euclid::default::Size2D; use fnv::FnvHashMap; use glow::{ @@ -43,7 +44,6 @@ use webrender_api::{ DirtyRect, DocumentId, ExternalImageData, ExternalImageId, ExternalImageType, ImageBufferKind, ImageData, ImageDescriptor, ImageDescriptorFlags, ImageFormat, ImageKey, }; -use webrender_traits::{WebrenderExternalImageRegistry, WebrenderImageHandlerType}; use crate::webgl_limits::GLLimitsDetect; #[cfg(feature = "webxr")] diff --git a/components/compositing/Cargo.toml b/components/compositing/Cargo.toml index 11d87635f32..6cabded02d8 100644 --- a/components/compositing/Cargo.toml +++ b/components/compositing/Cargo.toml @@ -41,7 +41,6 @@ stylo_traits = { workspace = true } tracing = { workspace = true, optional = true } webrender = { workspace = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } webxr = { path = "../webxr", optional = true } [dev-dependencies] diff --git a/components/compositing/compositor.rs b/components/compositing/compositor.rs index 9764d343b92..d4c522aa05e 100644 --- a/components/compositing/compositor.rs +++ b/components/compositing/compositor.rs @@ -16,8 +16,11 @@ use base::cross_process_instant::CrossProcessInstant; use base::id::{PipelineId, WebViewId}; use base::{Epoch, WebRenderEpochToU16}; use bitflags::bitflags; +use compositing_traits::display_list::{HitTestInfo, ScrollTree}; +use compositing_traits::rendering_context::RenderingContext; use compositing_traits::{ - CompositionPipeline, CompositorMsg, CompositorReceiver, SendableFrameTree, + CompositionPipeline, CompositorMsg, CompositorReceiver, CrossProcessCompositorMessage, + ImageUpdate, RendererWebView, SendableFrameTree, }; use constellation_traits::{ AnimationTickType, EmbedderToConstellationMessage, PaintMetricEvent, WindowSizeType, @@ -51,9 +54,6 @@ use webrender_api::{ RenderReasons, SampledScrollOffset, ScrollLocation, SpaceAndClipInfo, SpatialId, SpatialTreeItemKey, TransformStyle, }; -use webrender_traits::display_list::{HitTestInfo, ScrollTree}; -use webrender_traits::rendering_context::RenderingContext; -use webrender_traits::{CrossProcessCompositorMessage, ImageUpdate, RendererWebView}; use crate::InitialCompositorState; use crate::webview::{UnknownWebView, WebView}; diff --git a/components/compositing/lib.rs b/components/compositing/lib.rs index be91f584cb0..2e09fd0b1ab 100644 --- a/components/compositing/lib.rs +++ b/components/compositing/lib.rs @@ -7,6 +7,7 @@ use std::cell::Cell; use std::rc::Rc; +use compositing_traits::rendering_context::RenderingContext; use compositing_traits::{CompositorProxy, CompositorReceiver}; use constellation_traits::EmbedderToConstellationMessage; use crossbeam_channel::Sender; @@ -14,7 +15,6 @@ use embedder_traits::ShutdownState; use profile_traits::{mem, time}; use webrender::RenderApi; use webrender_api::DocumentId; -use webrender_traits::rendering_context::RenderingContext; pub use crate::compositor::IOCompositor; diff --git a/components/compositing/webview.rs b/components/compositing/webview.rs index 7b2e997c5d2..9e8136f28ad 100644 --- a/components/compositing/webview.rs +++ b/components/compositing/webview.rs @@ -8,7 +8,7 @@ use std::collections::hash_map::Keys; use std::rc::Rc; use base::id::{PipelineId, WebViewId}; -use compositing_traits::SendableFrameTree; +use compositing_traits::{RendererWebView, SendableFrameTree}; use constellation_traits::{EmbedderToConstellationMessage, ScrollState}; use embedder_traits::{ AnimationState, CompositorHitTestResult, InputEvent, MouseButton, MouseButtonAction, @@ -23,7 +23,6 @@ use webrender_api::units::{DeviceIntPoint, DevicePoint, DeviceRect, LayoutVector use webrender_api::{ ExternalScrollId, HitTestFlags, RenderReasons, SampledScrollOffset, ScrollLocation, }; -use webrender_traits::RendererWebView; use crate::IOCompositor; use crate::compositor::{PipelineDetails, ServoRenderer}; diff --git a/components/constellation/Cargo.toml b/components/constellation/Cargo.toml index 9bc1576fa62..19b452e2021 100644 --- a/components/constellation/Cargo.toml +++ b/components/constellation/Cargo.toml @@ -53,7 +53,6 @@ webgpu = { path = "../webgpu" } webgpu_traits = { workspace = true } webrender = { workspace = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } webxr-api = { workspace = true, features = ["ipc"] } [target.'cfg(any(target_os="macos", all(not(target_os = "windows"), not(target_os = "ios"), not(target_os="android"), not(target_env="ohos"), not(target_arch="arm"), not(target_arch="aarch64"))))'.dependencies] diff --git a/components/constellation/constellation.rs b/components/constellation/constellation.rs index a2809defdd6..e1a16e4174f 100644 --- a/components/constellation/constellation.rs +++ b/components/constellation/constellation.rs @@ -108,7 +108,9 @@ use bluetooth_traits::BluetoothRequest; use canvas_traits::ConstellationCanvasMsg; use canvas_traits::canvas::{CanvasId, CanvasMsg}; use canvas_traits::webgl::WebGLThreads; -use compositing_traits::{CompositorMsg, CompositorProxy, SendableFrameTree}; +use compositing_traits::{ + CompositorMsg, CompositorProxy, SendableFrameTree, WebrenderExternalImageRegistry, +}; use constellation_traits::{ AnimationTickType, AuxiliaryWebViewCreationRequest, AuxiliaryWebViewCreationResponse, BroadcastMsg, DocumentState, EmbedderToConstellationMessage, IFrameLoadInfo, @@ -164,7 +166,6 @@ use webgpu_traits::{WebGPU, WebGPURequest}; use webrender::RenderApi; use webrender::RenderApiSender; use webrender_api::{DocumentId, ImageKey}; -use webrender_traits::WebrenderExternalImageRegistry; use crate::browsingcontext::{ AllBrowsingContextsIterator, BrowsingContext, FullyActiveBrowsingContextsIterator, diff --git a/components/constellation/pipeline.rs b/components/constellation/pipeline.rs index 8095cd6f0ae..b6e546acd48 100644 --- a/components/constellation/pipeline.rs +++ b/components/constellation/pipeline.rs @@ -18,7 +18,9 @@ use base::id::{ #[cfg(feature = "bluetooth")] use bluetooth_traits::BluetoothRequest; use canvas_traits::webgl::WebGLPipeline; -use compositing_traits::{CompositionPipeline, CompositorMsg, CompositorProxy}; +use compositing_traits::{ + CompositionPipeline, CompositorMsg, CompositorProxy, CrossProcessCompositorApi, +}; use constellation_traits::{LoadData, SWManagerMsg, ScriptToConstellationChan}; use crossbeam_channel::{Sender, unbounded}; use devtools_traits::{DevtoolsControlMsg, ScriptToDevtoolsControlMsg}; @@ -46,7 +48,6 @@ use servo_config::opts::{self, Opts}; use servo_config::prefs::{self, Preferences}; use servo_url::ServoUrl; use webrender_api::DocumentId; -use webrender_traits::CrossProcessCompositorApi; use crate::event_loop::EventLoop; use crate::process_manager::Process; diff --git a/components/fonts/Cargo.toml b/components/fonts/Cargo.toml index ee8a4f36412..2323cb1b240 100644 --- a/components/fonts/Cargo.toml +++ b/components/fonts/Cargo.toml @@ -21,6 +21,7 @@ app_units = { workspace = true } atomic_refcell = { workspace = true } base = { workspace = true } bitflags = { workspace = true } +compositing_traits = { workspace = true } euclid = { workspace = true } fnv = { workspace = true } fonts_traits = { workspace = true } @@ -50,7 +51,6 @@ unicode-properties = { workspace = true } unicode-script = { workspace = true } url = { workspace = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } [target.'cfg(target_os = "macos")'.dependencies] byteorder = { workspace = true } diff --git a/components/fonts/font_context.rs b/components/fonts/font_context.rs index b11a922abdf..81a730ed951 100644 --- a/components/fonts/font_context.rs +++ b/components/fonts/font_context.rs @@ -10,6 +10,7 @@ use std::sync::atomic::{AtomicBool, Ordering}; use app_units::Au; use base::id::WebViewId; +use compositing_traits::CrossProcessCompositorApi; use fnv::FnvHasher; use fonts_traits::StylesheetWebFontLoadFinishedCallback; use log::{debug, trace}; @@ -32,7 +33,6 @@ use style::stylesheets::{CssRule, DocumentStyleSheet, FontFaceRule, StylesheetIn use style::values::computed::font::{FamilyName, FontFamilyNameSyntax, SingleFontFamily}; use url::Url; use webrender_api::{FontInstanceFlags, FontInstanceKey, FontKey}; -use webrender_traits::CrossProcessCompositorApi; use crate::font::{ Font, FontDescriptor, FontFamilyDescriptor, FontGroup, FontRef, FontSearchScope, diff --git a/components/fonts/system_font_service.rs b/components/fonts/system_font_service.rs index 61b36e699df..91b2d810eff 100644 --- a/components/fonts/system_font_service.rs +++ b/components/fonts/system_font_service.rs @@ -11,6 +11,7 @@ use std::{fmt, thread}; use app_units::Au; use atomic_refcell::AtomicRefCell; +use compositing_traits::CrossProcessCompositorApi; use ipc_channel::ipc::{self, IpcReceiver, IpcSender}; use log::debug; use malloc_size_of_derive::MallocSizeOf; @@ -25,7 +26,6 @@ use style::values::computed::font::{ use style::values::computed::{FontStretch, FontWeight}; use style::values::specified::FontStretch as SpecifiedFontStretch; use webrender_api::{FontInstanceFlags, FontInstanceKey, FontKey}; -use webrender_traits::CrossProcessCompositorApi; use crate::font::FontDescriptor; use crate::font_store::FontStore; diff --git a/components/fonts/tests/font_context.rs b/components/fonts/tests/font_context.rs index ed102069eee..aeafa02bcc1 100644 --- a/components/fonts/tests/font_context.rs +++ b/components/fonts/tests/font_context.rs @@ -14,6 +14,7 @@ mod font_context { use std::thread; use app_units::Au; + use compositing_traits::CrossProcessCompositorApi; use fonts::platform::font::PlatformFont; use fonts::{ FallbackFontSelectionOptions, FontContext, FontDescriptor, FontFamilyDescriptor, @@ -34,7 +35,6 @@ mod font_context { }; use stylo_atoms::Atom; use webrender_api::{FontInstanceKey, FontKey, IdNamespace}; - use webrender_traits::CrossProcessCompositorApi; struct TestContext { context: FontContext, diff --git a/components/layout_2020/Cargo.toml b/components/layout_2020/Cargo.toml index b0cb2d05ba7..30fb8843d67 100644 --- a/components/layout_2020/Cargo.toml +++ b/components/layout_2020/Cargo.toml @@ -22,6 +22,7 @@ atomic_refcell = { workspace = true } base = { workspace = true } bitflags = { workspace = true } canvas_traits = { workspace = true } +compositing_traits = { workspace = true } data-url = { workspace = true } embedder_traits = { workspace = true } euclid = { workspace = true } @@ -54,7 +55,6 @@ unicode-bidi = { workspace = true } unicode-script = { workspace = true } url = { workspace = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } xi-unicode = { workspace = true } [dev-dependencies] diff --git a/components/layout_2020/display_list/mod.rs b/components/layout_2020/display_list/mod.rs index d6f9b533337..0e71f8505dc 100644 --- a/components/layout_2020/display_list/mod.rs +++ b/components/layout_2020/display_list/mod.rs @@ -8,6 +8,7 @@ use std::sync::Arc; use app_units::Au; use base::WebRenderEpochToU16; use base::id::ScrollTreeNodeId; +use compositing_traits::display_list::{AxesScrollSensitivity, CompositorDisplayListInfo}; use embedder_traits::Cursor; use euclid::{Point2D, SideOffsets2D, Size2D, UnknownUnit}; use fonts::GlyphStore; @@ -34,7 +35,6 @@ use webrender_api::{ self as wr, BorderDetails, BoxShadowClipMode, ClipChainId, CommonItemProperties, ImageRendering, NinePatchBorder, NinePatchBorderSource, units, }; -use webrender_traits::display_list::{AxesScrollSensitivity, CompositorDisplayListInfo}; use wr::units::LayoutVector2D; use crate::context::{LayoutContext, ResolvedImage}; diff --git a/components/layout_2020/display_list/stacking_context.rs b/components/layout_2020/display_list/stacking_context.rs index ece8502c21e..0c0def9a563 100644 --- a/components/layout_2020/display_list/stacking_context.rs +++ b/components/layout_2020/display_list/stacking_context.rs @@ -9,6 +9,7 @@ use std::mem; use app_units::Au; use base::id::ScrollTreeNodeId; use base::print_tree::PrintTree; +use compositing_traits::display_list::{AxesScrollSensitivity, ScrollableNodeInfo}; use euclid::SideOffsets2D; use euclid::default::{Point2D, Rect, Size2D}; use log::warn; @@ -28,7 +29,6 @@ use style::values::generics::transform::{self, GenericRotate, GenericScale, Gene use style::values::specified::box_::DisplayOutside; use webrender_api::units::{LayoutPoint, LayoutRect, LayoutTransform, LayoutVector2D}; use webrender_api::{self as wr, BorderRadius}; -use webrender_traits::display_list::{AxesScrollSensitivity, ScrollableNodeInfo}; use wr::units::{LayoutPixel, LayoutSize}; use wr::{ClipChainId, SpatialTreeItemKey, StickyOffsetBounds}; diff --git a/components/layout_2020/flow/root.rs b/components/layout_2020/flow/root.rs index 4fb33bf71d4..d784082e196 100644 --- a/components/layout_2020/flow/root.rs +++ b/components/layout_2020/flow/root.rs @@ -4,6 +4,7 @@ use app_units::Au; use atomic_refcell::AtomicRef; +use compositing_traits::display_list::AxesScrollSensitivity; use script_layout_interface::wrapper_traits::{ LayoutNode, ThreadSafeLayoutElement, ThreadSafeLayoutNode, }; @@ -13,7 +14,6 @@ use style::dom::OpaqueNode; use style::properties::ComputedValues; use style::values::computed::Overflow; use style_traits::CSSPixel; -use webrender_traits::display_list::AxesScrollSensitivity; use crate::cell::ArcRefCell; use crate::context::LayoutContext; diff --git a/components/layout_2020/fragment_tree/fragment_tree.rs b/components/layout_2020/fragment_tree/fragment_tree.rs index cc9c6abba18..32542ccd155 100644 --- a/components/layout_2020/fragment_tree/fragment_tree.rs +++ b/components/layout_2020/fragment_tree/fragment_tree.rs @@ -4,12 +4,12 @@ use app_units::Au; use base::print_tree::PrintTree; +use compositing_traits::display_list::AxesScrollSensitivity; use euclid::default::{Point2D, Rect, Size2D}; use fxhash::FxHashSet; use style::animation::AnimationSetKey; use style::dom::OpaqueNode; use webrender_api::units; -use webrender_traits::display_list::AxesScrollSensitivity; use super::{ContainingBlockManager, Fragment, Tag}; use crate::display_list::StackingContext; diff --git a/components/layout_thread_2020/Cargo.toml b/components/layout_thread_2020/Cargo.toml index 0bf77400403..dba63a79404 100644 --- a/components/layout_thread_2020/Cargo.toml +++ b/components/layout_thread_2020/Cargo.toml @@ -17,6 +17,7 @@ tracing = ["dep:tracing", "layout/tracing"] [dependencies] app_units = { workspace = true } base = { workspace = true } +compositing_traits = { workspace = true } constellation_traits = { workspace = true } embedder_traits = { workspace = true } euclid = { workspace = true } @@ -45,4 +46,3 @@ stylo_traits = { workspace = true } tracing = { workspace = true, optional = true } url = { workspace = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } diff --git a/components/layout_thread_2020/lib.rs b/components/layout_thread_2020/lib.rs index 9639275608b..f564f93790b 100644 --- a/components/layout_thread_2020/lib.rs +++ b/components/layout_thread_2020/lib.rs @@ -17,6 +17,7 @@ use std::sync::{Arc, LazyLock}; use app_units::Au; use base::Epoch; use base::id::{PipelineId, WebViewId}; +use compositing_traits::CrossProcessCompositorApi; use constellation_traits::ScrollState; use embedder_traits::resources::{self, Resource}; use embedder_traits::{UntrustedNodeAddress, ViewportDetails}; @@ -87,7 +88,6 @@ use stylo_atoms::Atom; use url::Url; use webrender_api::units::{DevicePixel, LayoutPixel}; use webrender_api::{ExternalScrollId, HitTestFlags, units}; -use webrender_traits::CrossProcessCompositorApi; // This mutex is necessary due to syncronisation issues between two different types of thread-local storage // which manifest themselves when the layout thread tries to layout iframes in parallel with the main page diff --git a/components/media/Cargo.toml b/components/media/Cargo.toml index 4e21db50bc8..cf51080ec7a 100644 --- a/components/media/Cargo.toml +++ b/components/media/Cargo.toml @@ -12,6 +12,7 @@ name = "media" path = "lib.rs" [dependencies] +compositing_traits = { workspace = true } euclid = { workspace = true } fnv = { workspace = true } ipc-channel = { workspace = true } @@ -20,4 +21,3 @@ serde = { workspace = true } servo-media = { workspace = true } servo_config = { path = "../config" } webrender_api = { workspace = true } -webrender_traits = { workspace = true } diff --git a/components/media/lib.rs b/components/media/lib.rs index 69b60b62275..2d45d38b8ca 100644 --- a/components/media/lib.rs +++ b/components/media/lib.rs @@ -9,16 +9,16 @@ mod media_thread; use std::sync::{Arc, Mutex}; +use compositing_traits::{ + WebrenderExternalImageApi, WebrenderExternalImageHandlers, WebrenderExternalImageRegistry, + WebrenderImageHandlerType, WebrenderImageSource, +}; use euclid::default::Size2D; use ipc_channel::ipc::{IpcReceiver, IpcSender, channel}; use log::warn; use serde::{Deserialize, Serialize}; use servo_config::pref; pub use servo_media::player::context::{GlApi, GlContext, NativeDisplay, PlayerGLContext}; -use webrender_traits::{ - WebrenderExternalImageApi, WebrenderExternalImageHandlers, WebrenderExternalImageRegistry, - WebrenderImageHandlerType, WebrenderImageSource, -}; use crate::media_thread::GLPlayerThread; diff --git a/components/media/media_thread.rs b/components/media/media_thread.rs index 7972ac9e70c..44551fd488d 100644 --- a/components/media/media_thread.rs +++ b/components/media/media_thread.rs @@ -5,11 +5,11 @@ use std::sync::{Arc, Mutex}; use std::thread; +use compositing_traits::{WebrenderExternalImageRegistry, WebrenderImageHandlerType}; use fnv::FnvHashMap; use ipc_channel::ipc::{IpcSender, channel}; use log::{trace, warn}; use webrender_api::ExternalImageId; -use webrender_traits::{WebrenderExternalImageRegistry, WebrenderImageHandlerType}; /// GL player threading API entry point that lives in the /// constellation. diff --git a/components/net/Cargo.toml b/components/net/Cargo.toml index abdc63259e7..6ecd746812a 100644 --- a/components/net/Cargo.toml +++ b/components/net/Cargo.toml @@ -22,6 +22,7 @@ base = { workspace = true } base64 = { workspace = true } bytes = "1" chrono = { workspace = true } +compositing_traits = { workspace = true } content-security-policy = { workspace = true } cookie = { workspace = true } crossbeam-channel = { workspace = true } @@ -71,7 +72,6 @@ url = { workspace = true } uuid = { workspace = true } webpki-roots = { workspace = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } [dev-dependencies] flate2 = "1" diff --git a/components/net/image_cache.rs b/components/net/image_cache.rs index dea123054ad..1e87467ca7f 100644 --- a/components/net/image_cache.rs +++ b/components/net/image_cache.rs @@ -7,6 +7,7 @@ use std::collections::hash_map::Entry::{Occupied, Vacant}; use std::sync::{Arc, Mutex}; use std::{mem, thread}; +use compositing_traits::{CrossProcessCompositorApi, SerializableImageData}; use imsz::imsz_from_reader; use ipc_channel::ipc::IpcSharedMemory; use log::{debug, warn}; @@ -21,7 +22,6 @@ use servo_config::pref; use servo_url::{ImmutableOrigin, ServoUrl}; use webrender_api::units::DeviceIntSize; use webrender_api::{ImageDescriptor, ImageDescriptorFlags, ImageFormat}; -use webrender_traits::{CrossProcessCompositorApi, SerializableImageData}; use crate::resource_thread::CoreResourceThreadPool; diff --git a/components/script/Cargo.toml b/components/script/Cargo.toml index 872ae7d6da5..691afd3935e 100644 --- a/components/script/Cargo.toml +++ b/components/script/Cargo.toml @@ -49,6 +49,7 @@ canvas_traits = { workspace = true } cbc = { workspace = true } chrono = { workspace = true } cipher = { workspace = true } +compositing_traits = { workspace = true } constellation_traits = { workspace = true } content-security-policy = { workspace = true } cookie = { workspace = true } @@ -134,7 +135,6 @@ uuid = { workspace = true, features = ["serde"] } webdriver = { workspace = true } webgpu_traits = { workspace = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } webxr-api = { workspace = true, features = ["ipc"], optional = true } wgpu-core = { workspace = true } wgpu-types = { workspace = true } diff --git a/components/script/dom/htmlmediaelement.rs b/components/script/dom/htmlmediaelement.rs index 64bd48b0c2f..b16c17f1d79 100644 --- a/components/script/dom/htmlmediaelement.rs +++ b/components/script/dom/htmlmediaelement.rs @@ -9,6 +9,7 @@ use std::sync::{Arc, Mutex}; use std::time::{Duration, Instant}; use std::{f64, mem}; +use compositing_traits::{CrossProcessCompositorApi, ImageUpdate, SerializableImageData}; use dom_struct::dom_struct; use embedder_traits::resources::{self, Resource as EmbedderResource}; use embedder_traits::{MediaPositionState, MediaSessionEvent, MediaSessionPlaybackState}; @@ -41,7 +42,6 @@ use webrender_api::{ ExternalImageData, ExternalImageId, ExternalImageType, ImageBufferKind, ImageDescriptor, ImageDescriptorFlags, ImageFormat, ImageKey, }; -use webrender_traits::{CrossProcessCompositorApi, ImageUpdate, SerializableImageData}; use crate::document_loader::{LoadBlocker, LoadType}; use crate::dom::attr::Attr; diff --git a/components/script/dom/screen.rs b/components/script/dom/screen.rs index 0d5a751e273..4d76b20d626 100644 --- a/components/script/dom/screen.rs +++ b/components/script/dom/screen.rs @@ -2,12 +2,12 @@ * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at https://mozilla.org/MPL/2.0/. */ +use compositing_traits::CrossProcessCompositorMessage; use dom_struct::dom_struct; use euclid::Size2D; use profile_traits::ipc; use servo_geometry::DeviceIndependentIntSize; use style_traits::CSSPixel; -use webrender_traits::CrossProcessCompositorMessage; use crate::dom::bindings::codegen::Bindings::ScreenBinding::ScreenMethods; use crate::dom::bindings::num::Finite; diff --git a/components/script/dom/window.rs b/components/script/dom/window.rs index c73caab123f..863c2299081 100644 --- a/components/script/dom/window.rs +++ b/components/script/dom/window.rs @@ -21,6 +21,7 @@ use base64::Engine; #[cfg(feature = "bluetooth")] use bluetooth_traits::BluetoothRequest; use canvas_traits::webgl::WebGLChan; +use compositing_traits::CrossProcessCompositorApi; use constellation_traits::{ DocumentState, LoadData, LoadOrigin, NavigationHistoryBehavior, ScriptToConstellationChan, ScriptToConstellationMessage, ScrollState, StructuredSerializedData, WindowSizeType, @@ -86,7 +87,6 @@ use stylo_atoms::Atom; use url::Position; use webrender_api::units::{DevicePixel, LayoutPixel}; use webrender_api::{DocumentId, ExternalScrollId}; -use webrender_traits::CrossProcessCompositorApi; use super::bindings::codegen::Bindings::MessagePortBinding::StructuredSerializeOptions; use super::bindings::trace::HashMapTracedValues; @@ -1895,7 +1895,7 @@ impl Window { let (sender, receiver) = ProfiledIpc::channel::(timer_profile_chan).unwrap(); let _ = self.compositor_api.sender().send( - webrender_traits::CrossProcessCompositorMessage::GetClientWindowRect( + compositing_traits::CrossProcessCompositorMessage::GetClientWindowRect( self.webview_id(), sender, ), diff --git a/components/script/script_thread.rs b/components/script/script_thread.rs index adf28bb7090..cc97c172490 100644 --- a/components/script/script_thread.rs +++ b/components/script/script_thread.rs @@ -36,6 +36,7 @@ use base::cross_process_instant::CrossProcessInstant; use base::id::{BrowsingContextId, HistoryStateId, PipelineId, PipelineNamespace, WebViewId}; use canvas_traits::webgl::WebGLPipeline; use chrono::{DateTime, Local}; +use compositing_traits::CrossProcessCompositorApi; use constellation_traits::{ JsEvalResult, LoadData, LoadOrigin, NavigationHistoryBehavior, ScriptToConstellationChan, ScriptToConstellationMessage, ScrollState, StructuredSerializedData, WindowSizeType, @@ -95,7 +96,6 @@ use url::Position; #[cfg(feature = "webgpu")] use webgpu_traits::{WebGPUDevice, WebGPUMsg}; use webrender_api::DocumentId; -use webrender_traits::CrossProcessCompositorApi; use crate::document_collection::DocumentCollection; use crate::document_loader::DocumentLoader; diff --git a/components/servo/Cargo.toml b/components/servo/Cargo.toml index d72665f9c4c..37468593ef0 100644 --- a/components/servo/Cargo.toml +++ b/components/servo/Cargo.toml @@ -31,7 +31,7 @@ js_backtrace = ["script/js_backtrace"] media-gstreamer = ["servo-media-gstreamer", "gstreamer"] multiview = ["compositing/multiview", "constellation/multiview"] native-bluetooth = ["bluetooth/native-bluetooth"] -no-wgl = ["mozangle/egl", "mozangle/build_dlls", "surfman/sm-angle-default", "webrender_traits/no-wgl"] +no-wgl = ["mozangle/egl", "mozangle/build_dlls", "surfman/sm-angle-default", "compositing_traits/no-wgl"] dynamic_freetype = ["webrender/dynamic_freetype"] profilemozjs = ["script/profilemozjs"] refcell_backtrace = ["script/refcell_backtrace"] @@ -110,7 +110,6 @@ webdriver_server = { path = "../webdriver_server", optional = true } webgpu = { path = "../webgpu" } webrender = { workspace = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } webxr-api = { workspace = true, optional = true } [target.'cfg(any(target_os = "android", target_env = "ohos"))'.dependencies] diff --git a/components/servo/lib.rs b/components/servo/lib.rs index 085a70edae2..3ef27875d3a 100644 --- a/components/servo/lib.rs +++ b/components/servo/lib.rs @@ -44,7 +44,13 @@ use canvas_traits::webgl::{GlType, WebGLThreads}; use clipboard_delegate::StringRequest; use compositing::windowing::{EmbedderMethods, WindowMethods}; use compositing::{IOCompositor, InitialCompositorState}; -use compositing_traits::{CompositorMsg, CompositorProxy, CompositorReceiver}; +pub use compositing_traits::rendering_context::{ + OffscreenRenderingContext, RenderingContext, SoftwareRenderingContext, WindowRenderingContext, +}; +use compositing_traits::{ + CompositorMsg, CompositorProxy, CompositorReceiver, CrossProcessCompositorApi, + WebrenderExternalImageHandlers, WebrenderExternalImageRegistry, WebrenderImageHandlerType, +}; #[cfg(all( not(target_os = "windows"), not(target_os = "ios"), @@ -98,13 +104,6 @@ pub use webgpu; use webgpu::swapchain::WGPUImageMap; use webrender::{ONE_TIME_USAGE_HINT, RenderApiSender, ShaderPrecacheFlags, UploadMethod}; use webrender_api::{ColorF, DocumentId, FramePublishId}; -pub use webrender_traits::rendering_context::{ - OffscreenRenderingContext, RenderingContext, SoftwareRenderingContext, WindowRenderingContext, -}; -use webrender_traits::{ - CrossProcessCompositorApi, WebrenderExternalImageHandlers, WebrenderExternalImageRegistry, - WebrenderImageHandlerType, -}; use webview::WebViewInner; #[cfg(feature = "webxr")] pub use webxr; diff --git a/components/servo/webview.rs b/components/servo/webview.rs index 42bac60fc52..ed243d56421 100644 --- a/components/servo/webview.rs +++ b/components/servo/webview.rs @@ -10,6 +10,7 @@ use std::time::Duration; use base::id::WebViewId; use compositing::IOCompositor; use compositing::windowing::WebRenderDebugOption; +use compositing_traits::RendererWebView; use constellation_traits::{EmbedderToConstellationMessage, TraversalDirection}; use dpi::PhysicalSize; use embedder_traits::{ @@ -18,7 +19,6 @@ use embedder_traits::{ use url::Url; use webrender_api::ScrollLocation; use webrender_api::units::{DeviceIntPoint, DeviceRect}; -use webrender_traits::RendererWebView; use crate::ConstellationProxy; use crate::clipboard_delegate::{ClipboardDelegate, DefaultClipboardDelegate}; diff --git a/components/shared/compositing/Cargo.toml b/components/shared/compositing/Cargo.toml index 02488755cff..d1df90106cb 100644 --- a/components/shared/compositing/Cargo.toml +++ b/components/shared/compositing/Cargo.toml @@ -11,16 +11,27 @@ rust-version.workspace = true name = "compositing_traits" path = "lib.rs" +[features] +no-wgl = ["surfman/sm-angle-default"] + [dependencies] base = { workspace = true } crossbeam-channel = { workspace = true } +dpi = { version = "0.1" } embedder_traits = { workspace = true } euclid = { workspace = true } +gleam = { workspace = true } +glow = { workspace = true } +image = { workspace = true } ipc-channel = { workspace = true } log = { workspace = true } pixels = { path = '../../pixels' } -script_traits = { workspace = true } +raw-window-handle = { version = "0.6" } +serde = { workspace = true } +servo_geometry = { path = "../../geometry" } strum_macros = { workspace = true } +stylo = { workspace = true } stylo_traits = { workspace = true } +surfman = { workspace = true, features = ["sm-x11"] } webrender_api = { workspace = true } -webrender_traits = { workspace = true } + diff --git a/components/shared/webrender/display_list.rs b/components/shared/compositing/display_list.rs similarity index 100% rename from components/shared/webrender/display_list.rs rename to components/shared/compositing/display_list.rs diff --git a/components/shared/compositing/lib.rs b/components/shared/compositing/lib.rs index 9c13afb8dc3..c231960ef50 100644 --- a/components/shared/compositing/lib.rs +++ b/components/shared/compositing/lib.rs @@ -18,7 +18,27 @@ use pixels::Image; use strum_macros::IntoStaticStr; use style_traits::CSSPixel; use webrender_api::DocumentId; -use webrender_traits::{CrossProcessCompositorApi, CrossProcessCompositorMessage}; + +pub mod display_list; +pub mod rendering_context; + +use core::fmt; +use std::collections::HashMap; +use std::sync::{Arc, Mutex}; + +use display_list::CompositorDisplayListInfo; +use embedder_traits::{CompositorHitTestResult, ScreenGeometry}; +use euclid::default::Size2D as UntypedSize2D; +use ipc_channel::ipc::{self, IpcSharedMemory}; +use serde::{Deserialize, Serialize}; +use servo_geometry::{DeviceIndependentIntRect, DeviceIndependentIntSize}; +use webrender_api::units::{DevicePoint, LayoutPoint, TexelRect}; +use webrender_api::{ + BuiltDisplayList, BuiltDisplayListDescriptor, ExternalImage, ExternalImageData, + ExternalImageHandler, ExternalImageId, ExternalImageSource, ExternalScrollId, + FontInstanceFlags, FontInstanceKey, FontKey, HitTestFlags, ImageData, ImageDescriptor, + ImageKey, NativeFontHandle, PipelineId as WebRenderPipelineId, +}; /// Sends messages to the compositor. #[derive(Clone)] @@ -111,3 +131,463 @@ impl Debug for CompositorMsg { write!(formatter, "{string}") } } + +#[derive(Deserialize, Serialize)] +pub enum CrossProcessCompositorMessage { + /// Inform WebRender of the existence of this pipeline. + SendInitialTransaction(WebRenderPipelineId), + /// Perform a scroll operation. + SendScrollNode( + WebViewId, + WebRenderPipelineId, + LayoutPoint, + ExternalScrollId, + ), + /// Inform WebRender of a new display list for the given pipeline. + SendDisplayList { + /// The [`WebViewId`] that this display list belongs to. + webview_id: WebViewId, + /// The [CompositorDisplayListInfo] that describes the display list being sent. + display_list_info: Box, + /// A descriptor of this display list used to construct this display list from raw data. + display_list_descriptor: BuiltDisplayListDescriptor, + /// An [ipc::IpcBytesReceiver] used to send the raw data of the display list. + display_list_receiver: ipc::IpcBytesReceiver, + }, + /// Perform a hit test operation. The result will be returned via + /// the provided channel sender. + HitTest( + Option, + DevicePoint, + HitTestFlags, + IpcSender>, + ), + /// Create a new image key. The result will be returned via the + /// provided channel sender. + GenerateImageKey(IpcSender), + /// Add an image with the given data and `ImageKey`. + AddImage(ImageKey, ImageDescriptor, SerializableImageData), + /// Perform a resource update operation. + UpdateImages(Vec), + + /// Generate a new batch of font keys which can be used to allocate + /// keys asynchronously. + GenerateFontKeys( + usize, + usize, + IpcSender<(Vec, Vec)>, + ), + /// Add a font with the given data and font key. + AddFont(FontKey, Arc, u32), + /// Add a system font with the given font key and handle. + AddSystemFont(FontKey, NativeFontHandle), + /// Add an instance of a font with the given instance key. + AddFontInstance(FontInstanceKey, FontKey, f32, FontInstanceFlags), + /// Remove the given font resources from our WebRender instance. + RemoveFonts(Vec, Vec), + + /// Get the client window size and position. + GetClientWindowRect(WebViewId, IpcSender), + /// Get the size of the screen that the client window inhabits. + GetScreenSize(WebViewId, IpcSender), + /// Get the available screen size (without toolbars and docks) for the screen + /// the client window inhabits. + GetAvailableScreenSize(WebViewId, IpcSender), +} + +impl fmt::Debug for CrossProcessCompositorMessage { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + match self { + Self::AddImage(..) => f.write_str("AddImage"), + Self::GenerateFontKeys(..) => f.write_str("GenerateFontKeys"), + Self::AddSystemFont(..) => f.write_str("AddSystemFont"), + Self::SendInitialTransaction(..) => f.write_str("SendInitialTransaction"), + Self::SendScrollNode(..) => f.write_str("SendScrollNode"), + Self::SendDisplayList { .. } => f.write_str("SendDisplayList"), + Self::HitTest(..) => f.write_str("HitTest"), + Self::GenerateImageKey(..) => f.write_str("GenerateImageKey"), + Self::UpdateImages(..) => f.write_str("UpdateImages"), + Self::RemoveFonts(..) => f.write_str("RemoveFonts"), + Self::AddFontInstance(..) => f.write_str("AddFontInstance"), + Self::AddFont(..) => f.write_str("AddFont"), + Self::GetClientWindowRect(..) => f.write_str("GetClientWindowRect"), + Self::GetScreenSize(..) => f.write_str("GetScreenSize"), + Self::GetAvailableScreenSize(..) => f.write_str("GetAvailableScreenSize"), + } + } +} + +/// A mechanism to send messages from ScriptThread to the parent process' WebRender instance. +#[derive(Clone, Deserialize, Serialize)] +pub struct CrossProcessCompositorApi(pub IpcSender); + +impl CrossProcessCompositorApi { + /// Create a new [`CrossProcessCompositorApi`] struct that does not have a listener on the other + /// end to use for unit testing. + pub fn dummy() -> Self { + let (sender, _) = ipc::channel().unwrap(); + Self(sender) + } + + /// Get the sender for this proxy. + pub fn sender(&self) -> &IpcSender { + &self.0 + } + + /// Inform WebRender of the existence of this pipeline. + pub fn send_initial_transaction(&self, pipeline: WebRenderPipelineId) { + if let Err(e) = self + .0 + .send(CrossProcessCompositorMessage::SendInitialTransaction( + pipeline, + )) + { + warn!("Error sending initial transaction: {}", e); + } + } + + /// Perform a scroll operation. + pub fn send_scroll_node( + &self, + webview_id: WebViewId, + pipeline_id: WebRenderPipelineId, + point: LayoutPoint, + scroll_id: ExternalScrollId, + ) { + if let Err(e) = self.0.send(CrossProcessCompositorMessage::SendScrollNode( + webview_id, + pipeline_id, + point, + scroll_id, + )) { + warn!("Error sending scroll node: {}", e); + } + } + + /// Inform WebRender of a new display list for the given pipeline. + pub fn send_display_list( + &self, + webview_id: WebViewId, + display_list_info: CompositorDisplayListInfo, + list: BuiltDisplayList, + ) { + let (display_list_data, display_list_descriptor) = list.into_data(); + let (display_list_sender, display_list_receiver) = ipc::bytes_channel().unwrap(); + if let Err(e) = self.0.send(CrossProcessCompositorMessage::SendDisplayList { + webview_id, + display_list_info: Box::new(display_list_info), + display_list_descriptor, + display_list_receiver, + }) { + warn!("Error sending display list: {}", e); + } + + if let Err(error) = display_list_sender.send(&display_list_data.items_data) { + warn!("Error sending display list items: {}", error); + } + if let Err(error) = display_list_sender.send(&display_list_data.cache_data) { + warn!("Error sending display list cache data: {}", error); + } + if let Err(error) = display_list_sender.send(&display_list_data.spatial_tree) { + warn!("Error sending display spatial tree: {}", error); + } + } + + /// Perform a hit test operation. Blocks until the operation is complete and + /// and a result is available. + pub fn hit_test( + &self, + pipeline: Option, + point: DevicePoint, + flags: HitTestFlags, + ) -> Vec { + let (sender, receiver) = ipc::channel().unwrap(); + self.0 + .send(CrossProcessCompositorMessage::HitTest( + pipeline, point, flags, sender, + )) + .expect("error sending hit test"); + receiver.recv().expect("error receiving hit test result") + } + + /// Create a new image key. Blocks until the key is available. + pub fn generate_image_key(&self) -> Option { + let (sender, receiver) = ipc::channel().unwrap(); + self.0 + .send(CrossProcessCompositorMessage::GenerateImageKey(sender)) + .ok()?; + receiver.recv().ok() + } + + pub fn add_image( + &self, + key: ImageKey, + descriptor: ImageDescriptor, + data: SerializableImageData, + ) { + if let Err(e) = self.0.send(CrossProcessCompositorMessage::AddImage( + key, descriptor, data, + )) { + warn!("Error sending image update: {}", e); + } + } + + /// Perform an image resource update operation. + pub fn update_images(&self, updates: Vec) { + if let Err(e) = self + .0 + .send(CrossProcessCompositorMessage::UpdateImages(updates)) + { + warn!("error sending image updates: {}", e); + } + } + + pub fn remove_unused_font_resources( + &self, + keys: Vec, + instance_keys: Vec, + ) { + if keys.is_empty() && instance_keys.is_empty() { + return; + } + let _ = self.0.send(CrossProcessCompositorMessage::RemoveFonts( + keys, + instance_keys, + )); + } + + pub fn add_font_instance( + &self, + font_instance_key: FontInstanceKey, + font_key: FontKey, + size: f32, + flags: FontInstanceFlags, + ) { + let _x = self.0.send(CrossProcessCompositorMessage::AddFontInstance( + font_instance_key, + font_key, + size, + flags, + )); + } + + pub fn add_font(&self, font_key: FontKey, data: Arc, index: u32) { + let _ = self.0.send(CrossProcessCompositorMessage::AddFont( + font_key, data, index, + )); + } + + pub fn add_system_font(&self, font_key: FontKey, handle: NativeFontHandle) { + let _ = self.0.send(CrossProcessCompositorMessage::AddSystemFont( + font_key, handle, + )); + } + + pub fn fetch_font_keys( + &self, + number_of_font_keys: usize, + number_of_font_instance_keys: usize, + ) -> (Vec, Vec) { + let (sender, receiver) = ipc_channel::ipc::channel().expect("Could not create IPC channel"); + let _ = self.0.send(CrossProcessCompositorMessage::GenerateFontKeys( + number_of_font_keys, + number_of_font_instance_keys, + sender, + )); + receiver.recv().unwrap() + } +} + +/// This trait is used as a bridge between the different GL clients +/// in Servo that handles WebRender ExternalImages and the WebRender +/// ExternalImageHandler API. +// +/// This trait is used to notify lock/unlock messages and get the +/// required info that WR needs. +pub trait WebrenderExternalImageApi { + fn lock(&mut self, id: u64) -> (WebrenderImageSource, UntypedSize2D); + fn unlock(&mut self, id: u64); +} + +pub enum WebrenderImageSource<'a> { + TextureHandle(u32), + Raw(&'a [u8]), +} + +/// Type of Webrender External Image Handler. +pub enum WebrenderImageHandlerType { + WebGL, + Media, + WebGPU, +} + +/// List of Webrender external images to be shared among all external image +/// consumers (WebGL, Media, WebGPU). +/// It ensures that external image identifiers are unique. +#[derive(Default)] +pub struct WebrenderExternalImageRegistry { + /// Map of all generated external images. + external_images: HashMap, + /// Id generator for the next external image identifier. + next_image_id: u64, +} + +impl WebrenderExternalImageRegistry { + pub fn next_id(&mut self, handler_type: WebrenderImageHandlerType) -> ExternalImageId { + self.next_image_id += 1; + let key = ExternalImageId(self.next_image_id); + self.external_images.insert(key, handler_type); + key + } + + pub fn remove(&mut self, key: &ExternalImageId) { + self.external_images.remove(key); + } + + pub fn get(&self, key: &ExternalImageId) -> Option<&WebrenderImageHandlerType> { + self.external_images.get(key) + } +} + +/// WebRender External Image Handler implementation. +pub struct WebrenderExternalImageHandlers { + /// WebGL handler. + webgl_handler: Option>, + /// Media player handler. + media_handler: Option>, + /// WebGPU handler. + webgpu_handler: Option>, + /// Webrender external images. + external_images: Arc>, +} + +impl WebrenderExternalImageHandlers { + pub fn new() -> (Self, Arc>) { + let external_images = Arc::new(Mutex::new(WebrenderExternalImageRegistry::default())); + ( + Self { + webgl_handler: None, + media_handler: None, + webgpu_handler: None, + external_images: external_images.clone(), + }, + external_images, + ) + } + + pub fn set_handler( + &mut self, + handler: Box, + handler_type: WebrenderImageHandlerType, + ) { + match handler_type { + WebrenderImageHandlerType::WebGL => self.webgl_handler = Some(handler), + WebrenderImageHandlerType::Media => self.media_handler = Some(handler), + WebrenderImageHandlerType::WebGPU => self.webgpu_handler = Some(handler), + } + } +} + +impl ExternalImageHandler for WebrenderExternalImageHandlers { + /// 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. + fn lock(&mut self, key: ExternalImageId, _channel_index: u8) -> ExternalImage { + let external_images = self.external_images.lock().unwrap(); + let handler_type = external_images + .get(&key) + .expect("Tried to get unknown external image"); + match handler_type { + WebrenderImageHandlerType::WebGL => { + let (source, size) = self.webgl_handler.as_mut().unwrap().lock(key.0); + let texture_id = match source { + WebrenderImageSource::TextureHandle(b) => b, + _ => panic!("Wrong type"), + }; + ExternalImage { + uv: TexelRect::new(0.0, size.height as f32, size.width as f32, 0.0), + source: ExternalImageSource::NativeTexture(texture_id), + } + }, + WebrenderImageHandlerType::Media => { + let (source, size) = self.media_handler.as_mut().unwrap().lock(key.0); + let texture_id = match source { + WebrenderImageSource::TextureHandle(b) => b, + _ => panic!("Wrong type"), + }; + ExternalImage { + uv: TexelRect::new(0.0, size.height as f32, size.width as f32, 0.0), + source: ExternalImageSource::NativeTexture(texture_id), + } + }, + WebrenderImageHandlerType::WebGPU => { + let (source, size) = self.webgpu_handler.as_mut().unwrap().lock(key.0); + let buffer = match source { + WebrenderImageSource::Raw(b) => b, + _ => panic!("Wrong type"), + }; + ExternalImage { + uv: TexelRect::new(0.0, size.height as f32, size.width as f32, 0.0), + source: ExternalImageSource::RawData(buffer), + } + }, + } + } + + /// Unlock the external image. The WR should not read the image + /// content after this call. + fn unlock(&mut self, key: ExternalImageId, _channel_index: u8) { + let external_images = self.external_images.lock().unwrap(); + let handler_type = external_images + .get(&key) + .expect("Tried to get unknown external image"); + match handler_type { + WebrenderImageHandlerType::WebGL => self.webgl_handler.as_mut().unwrap().unlock(key.0), + WebrenderImageHandlerType::Media => self.media_handler.as_mut().unwrap().unlock(key.0), + WebrenderImageHandlerType::WebGPU => { + self.webgpu_handler.as_mut().unwrap().unlock(key.0) + }, + }; + } +} + +#[derive(Deserialize, Serialize)] +/// Serializable image updates that must be performed by WebRender. +pub enum ImageUpdate { + /// Register a new image. + AddImage(ImageKey, ImageDescriptor, SerializableImageData), + /// Delete a previously registered image registration. + DeleteImage(ImageKey), + /// Update an existing image registration. + UpdateImage(ImageKey, ImageDescriptor, SerializableImageData), +} + +#[derive(Debug, Deserialize, Serialize)] +/// Serialized `ImageData`. It contains IPC byte channel receiver to prevent from loading bytes too +/// slow. +pub enum SerializableImageData { + /// A simple series of bytes, provided by the embedding and owned by WebRender. + /// The format is stored out-of-band, currently in ImageDescriptor. + Raw(IpcSharedMemory), + /// An image owned by the embedding, and referenced by WebRender. This may + /// take the form of a texture or a heap-allocated buffer. + External(ExternalImageData), +} + +impl From for ImageData { + fn from(value: SerializableImageData) -> Self { + match value { + SerializableImageData::Raw(shared_memory) => ImageData::new(shared_memory.to_vec()), + SerializableImageData::External(image) => ImageData::External(image), + } + } +} + +/// A trait that exposes the embedding layer's `WebView` to the Servo renderer. +/// This is to prevent a dependency cycle between the renderer and the embedding +/// layer. +pub trait RendererWebView { + fn id(&self) -> WebViewId; + fn screen_geometry(&self) -> Option; +} diff --git a/components/shared/webrender/rendering_context.rs b/components/shared/compositing/rendering_context.rs similarity index 100% rename from components/shared/webrender/rendering_context.rs rename to components/shared/compositing/rendering_context.rs diff --git a/components/shared/script/tests/compositor.rs b/components/shared/compositing/tests/compositor.rs similarity index 99% rename from components/shared/script/tests/compositor.rs rename to components/shared/compositing/tests/compositor.rs index fb8410cb282..4d2ecfd99c9 100644 --- a/components/shared/script/tests/compositor.rs +++ b/components/shared/compositing/tests/compositor.rs @@ -3,12 +3,12 @@ * file, You can obtain one at https://mozilla.org/MPL/2.0/. */ use base::id::ScrollTreeNodeId; +use compositing_traits::display_list::{ + AxesScrollSensitivity, ScrollSensitivity, ScrollTree, ScrollableNodeInfo, +}; use euclid::Size2D; use webrender_api::units::LayoutVector2D; use webrender_api::{ExternalScrollId, PipelineId, ScrollLocation, SpatialId}; -use webrender_traits::display_list::{ - AxesScrollSensitivity, ScrollSensitivity, ScrollTree, ScrollableNodeInfo, -}; fn add_mock_scroll_node(tree: &mut ScrollTree) -> ScrollTreeNodeId { let pipeline_id = PipelineId(0, 0); diff --git a/components/shared/net/Cargo.toml b/components/shared/net/Cargo.toml index 511460b4f98..d4b30fb86e5 100644 --- a/components/shared/net/Cargo.toml +++ b/components/shared/net/Cargo.toml @@ -15,6 +15,7 @@ doctest = false [dependencies] base = { workspace = true } +compositing_traits = { workspace = true } content-security-policy = { workspace = true } cookie = { workspace = true } crossbeam-channel = { workspace = true } @@ -38,4 +39,3 @@ servo_rand = { path = "../../rand" } servo_url = { path = "../../url" } url = { workspace = true } uuid = { workspace = true } -webrender_traits = { workspace = true } diff --git a/components/shared/net/image_cache.rs b/components/shared/net/image_cache.rs index abe0385c71a..7b6d364af58 100644 --- a/components/shared/net/image_cache.rs +++ b/components/shared/net/image_cache.rs @@ -5,13 +5,13 @@ use std::sync::Arc; use base::id::PipelineId; +use compositing_traits::CrossProcessCompositorApi; use ipc_channel::ipc::IpcSender; use log::debug; use malloc_size_of_derive::MallocSizeOf; use pixels::{Image, ImageMetadata}; use serde::{Deserialize, Serialize}; use servo_url::{ImmutableOrigin, ServoUrl}; -use webrender_traits::CrossProcessCompositorApi; use crate::FetchResponseMsg; use crate::request::CorsSettings; diff --git a/components/shared/script/Cargo.toml b/components/shared/script/Cargo.toml index 49efbadc165..0d3690188fe 100644 --- a/components/shared/script/Cargo.toml +++ b/components/shared/script/Cargo.toml @@ -20,6 +20,7 @@ background_hang_monitor_api = { workspace = true } base = { workspace = true } bluetooth_traits = { workspace = true, optional = true } canvas_traits = { workspace = true } +compositing_traits = { workspace = true } constellation_traits = { workspace = true } crossbeam-channel = { workspace = true } devtools_traits = { workspace = true } @@ -42,5 +43,4 @@ stylo_atoms = { workspace = true } stylo_traits = { workspace = true } webgpu_traits = { workspace = true, optional = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } webxr-api = { workspace = true, features = ["ipc"] } diff --git a/components/shared/script/lib.rs b/components/shared/script/lib.rs index 1a35f4f7486..5ee143b3cdd 100644 --- a/components/shared/script/lib.rs +++ b/components/shared/script/lib.rs @@ -18,6 +18,7 @@ use base::id::{BrowsingContextId, HistoryStateId, PipelineId, PipelineNamespaceI #[cfg(feature = "bluetooth")] use bluetooth_traits::BluetoothRequest; use canvas_traits::webgl::WebGLPipeline; +use compositing_traits::CrossProcessCompositorApi; use constellation_traits::{ AnimationTickType, LoadData, NavigationHistoryBehavior, ScriptToConstellationChan, ScrollState, StructuredSerializedData, WindowSizeType, @@ -48,7 +49,6 @@ use stylo_atoms::Atom; use webgpu_traits::WebGPUMsg; use webrender_api::units::DevicePixel; use webrender_api::{DocumentId, ImageKey}; -use webrender_traits::CrossProcessCompositorApi; /// The initial data required to create a new layout attached to an existing script thread. #[derive(Debug, Deserialize, Serialize)] diff --git a/components/shared/script_layout/Cargo.toml b/components/shared/script_layout/Cargo.toml index 5c0b6e01d36..06690192f73 100644 --- a/components/shared/script_layout/Cargo.toml +++ b/components/shared/script_layout/Cargo.toml @@ -16,6 +16,7 @@ base = { workspace = true } app_units = { workspace = true } atomic_refcell = { workspace = true } canvas_traits = { workspace = true } +compositing_traits = { workspace = true } constellation_traits = { workspace = true } embedder_traits = { workspace = true } euclid = { workspace = true } @@ -41,4 +42,3 @@ servo_url = { path = "../../url" } stylo = { workspace = true } stylo_traits = { workspace = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } diff --git a/components/shared/script_layout/lib.rs b/components/shared/script_layout/lib.rs index 6d686d75f03..ac1e332e3b6 100644 --- a/components/shared/script_layout/lib.rs +++ b/components/shared/script_layout/lib.rs @@ -18,6 +18,7 @@ use app_units::Au; use atomic_refcell::AtomicRefCell; use base::Epoch; use base::id::{BrowsingContextId, PipelineId, WebViewId}; +use compositing_traits::CrossProcessCompositorApi; use constellation_traits::{LoadData, ScrollState}; use embedder_traits::{UntrustedNodeAddress, ViewportDetails}; use euclid::default::{Point2D, Rect}; @@ -48,7 +49,6 @@ use style::queries::values::PrefersColorScheme; use style::selector_parser::{PseudoElement, RestyleDamage, Snapshot}; use style::stylesheets::Stylesheet; use webrender_api::ImageKey; -use webrender_traits::CrossProcessCompositorApi; pub type GenericLayoutData = dyn Any + Send + Sync; diff --git a/components/shared/webrender/Cargo.toml b/components/shared/webrender/Cargo.toml deleted file mode 100644 index b437174307d..00000000000 --- a/components/shared/webrender/Cargo.toml +++ /dev/null @@ -1,35 +0,0 @@ -[package] -name = "webrender_traits" -version.workspace = true -authors.workspace = true -license.workspace = true -edition.workspace = true -publish.workspace = true -rust-version.workspace = true - -[lib] -name = "webrender_traits" -path = "lib.rs" -test = true - -[features] -no-wgl = ["surfman/sm-angle-default"] - -[dependencies] -base = { workspace = true } -dpi = { version = "0.1" } -embedder_traits = { workspace = true } -euclid = { workspace = true } -gleam = { workspace = true } -glow = { workspace = true } -image = { workspace = true } -ipc-channel = { workspace = true } -libc = { workspace = true } -log = { workspace = true } -raw-window-handle = { version = "0.6" } -serde = { workspace = true } -servo-media = { workspace = true } -servo_geometry = { path = "../../geometry" } -stylo = { workspace = true } -surfman = { workspace = true, features = ["sm-x11"] } -webrender_api = { workspace = true } diff --git a/components/shared/webrender/lib.rs b/components/shared/webrender/lib.rs deleted file mode 100644 index 3438aeb28ef..00000000000 --- a/components/shared/webrender/lib.rs +++ /dev/null @@ -1,488 +0,0 @@ -/* This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at https://mozilla.org/MPL/2.0/. */ - -#![deny(unsafe_code)] - -pub mod display_list; -pub mod rendering_context; - -use core::fmt; -use std::collections::HashMap; -use std::sync::{Arc, Mutex}; - -use base::id::WebViewId; -use display_list::CompositorDisplayListInfo; -use embedder_traits::{CompositorHitTestResult, ScreenGeometry}; -use euclid::default::Size2D as UntypedSize2D; -use ipc_channel::ipc::{self, IpcSender, IpcSharedMemory}; -use log::warn; -use serde::{Deserialize, Serialize}; -use servo_geometry::{DeviceIndependentIntRect, DeviceIndependentIntSize}; -use webrender_api::units::{DevicePoint, LayoutPoint, TexelRect}; -use webrender_api::{ - BuiltDisplayList, BuiltDisplayListDescriptor, ExternalImage, ExternalImageData, - ExternalImageHandler, ExternalImageId, ExternalImageSource, ExternalScrollId, - FontInstanceFlags, FontInstanceKey, FontKey, HitTestFlags, ImageData, ImageDescriptor, - ImageKey, NativeFontHandle, PipelineId as WebRenderPipelineId, -}; - -#[derive(Deserialize, Serialize)] -pub enum CrossProcessCompositorMessage { - /// Inform WebRender of the existence of this pipeline. - SendInitialTransaction(WebRenderPipelineId), - /// Perform a scroll operation. - SendScrollNode( - WebViewId, - WebRenderPipelineId, - LayoutPoint, - ExternalScrollId, - ), - /// Inform WebRender of a new display list for the given pipeline. - SendDisplayList { - /// The [`WebViewId`] that this display list belongs to. - webview_id: WebViewId, - /// The [CompositorDisplayListInfo] that describes the display list being sent. - display_list_info: Box, - /// A descriptor of this display list used to construct this display list from raw data. - display_list_descriptor: BuiltDisplayListDescriptor, - /// An [ipc::IpcBytesReceiver] used to send the raw data of the display list. - display_list_receiver: ipc::IpcBytesReceiver, - }, - /// Perform a hit test operation. The result will be returned via - /// the provided channel sender. - HitTest( - Option, - DevicePoint, - HitTestFlags, - IpcSender>, - ), - /// Create a new image key. The result will be returned via the - /// provided channel sender. - GenerateImageKey(IpcSender), - /// Add an image with the given data and `ImageKey`. - AddImage(ImageKey, ImageDescriptor, SerializableImageData), - /// Perform a resource update operation. - UpdateImages(Vec), - - /// Generate a new batch of font keys which can be used to allocate - /// keys asynchronously. - GenerateFontKeys( - usize, - usize, - IpcSender<(Vec, Vec)>, - ), - /// Add a font with the given data and font key. - AddFont(FontKey, Arc, u32), - /// Add a system font with the given font key and handle. - AddSystemFont(FontKey, NativeFontHandle), - /// Add an instance of a font with the given instance key. - AddFontInstance(FontInstanceKey, FontKey, f32, FontInstanceFlags), - /// Remove the given font resources from our WebRender instance. - RemoveFonts(Vec, Vec), - - /// Get the client window size and position. - GetClientWindowRect(WebViewId, IpcSender), - /// Get the size of the screen that the client window inhabits. - GetScreenSize(WebViewId, IpcSender), - /// Get the available screen size (without toolbars and docks) for the screen - /// the client window inhabits. - GetAvailableScreenSize(WebViewId, IpcSender), -} - -impl fmt::Debug for CrossProcessCompositorMessage { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - match self { - Self::AddImage(..) => f.write_str("AddImage"), - Self::GenerateFontKeys(..) => f.write_str("GenerateFontKeys"), - Self::AddSystemFont(..) => f.write_str("AddSystemFont"), - Self::SendInitialTransaction(..) => f.write_str("SendInitialTransaction"), - Self::SendScrollNode(..) => f.write_str("SendScrollNode"), - Self::SendDisplayList { .. } => f.write_str("SendDisplayList"), - Self::HitTest(..) => f.write_str("HitTest"), - Self::GenerateImageKey(..) => f.write_str("GenerateImageKey"), - Self::UpdateImages(..) => f.write_str("UpdateImages"), - Self::RemoveFonts(..) => f.write_str("RemoveFonts"), - Self::AddFontInstance(..) => f.write_str("AddFontInstance"), - Self::AddFont(..) => f.write_str("AddFont"), - Self::GetClientWindowRect(..) => f.write_str("GetClientWindowRect"), - Self::GetScreenSize(..) => f.write_str("GetScreenSize"), - Self::GetAvailableScreenSize(..) => f.write_str("GetAvailableScreenSize"), - } - } -} - -/// A mechanism to send messages from ScriptThread to the parent process' WebRender instance. -#[derive(Clone, Deserialize, Serialize)] -pub struct CrossProcessCompositorApi(pub IpcSender); - -impl CrossProcessCompositorApi { - /// Create a new [`CrossProcessCompositorApi`] struct that does not have a listener on the other - /// end to use for unit testing. - pub fn dummy() -> Self { - let (sender, _) = ipc::channel().unwrap(); - Self(sender) - } - - /// Get the sender for this proxy. - pub fn sender(&self) -> &IpcSender { - &self.0 - } - - /// Inform WebRender of the existence of this pipeline. - pub fn send_initial_transaction(&self, pipeline: WebRenderPipelineId) { - if let Err(e) = self - .0 - .send(CrossProcessCompositorMessage::SendInitialTransaction( - pipeline, - )) - { - warn!("Error sending initial transaction: {}", e); - } - } - - /// Perform a scroll operation. - pub fn send_scroll_node( - &self, - webview_id: WebViewId, - pipeline_id: WebRenderPipelineId, - point: LayoutPoint, - scroll_id: ExternalScrollId, - ) { - if let Err(e) = self.0.send(CrossProcessCompositorMessage::SendScrollNode( - webview_id, - pipeline_id, - point, - scroll_id, - )) { - warn!("Error sending scroll node: {}", e); - } - } - - /// Inform WebRender of a new display list for the given pipeline. - pub fn send_display_list( - &self, - webview_id: WebViewId, - display_list_info: CompositorDisplayListInfo, - list: BuiltDisplayList, - ) { - let (display_list_data, display_list_descriptor) = list.into_data(); - let (display_list_sender, display_list_receiver) = ipc::bytes_channel().unwrap(); - if let Err(e) = self.0.send(CrossProcessCompositorMessage::SendDisplayList { - webview_id, - display_list_info: Box::new(display_list_info), - display_list_descriptor, - display_list_receiver, - }) { - warn!("Error sending display list: {}", e); - } - - if let Err(error) = display_list_sender.send(&display_list_data.items_data) { - warn!("Error sending display list items: {}", error); - } - if let Err(error) = display_list_sender.send(&display_list_data.cache_data) { - warn!("Error sending display list cache data: {}", error); - } - if let Err(error) = display_list_sender.send(&display_list_data.spatial_tree) { - warn!("Error sending display spatial tree: {}", error); - } - } - - /// Perform a hit test operation. Blocks until the operation is complete and - /// and a result is available. - pub fn hit_test( - &self, - pipeline: Option, - point: DevicePoint, - flags: HitTestFlags, - ) -> Vec { - let (sender, receiver) = ipc::channel().unwrap(); - self.0 - .send(CrossProcessCompositorMessage::HitTest( - pipeline, point, flags, sender, - )) - .expect("error sending hit test"); - receiver.recv().expect("error receiving hit test result") - } - - /// Create a new image key. Blocks until the key is available. - pub fn generate_image_key(&self) -> Option { - let (sender, receiver) = ipc::channel().unwrap(); - self.0 - .send(CrossProcessCompositorMessage::GenerateImageKey(sender)) - .ok()?; - receiver.recv().ok() - } - - pub fn add_image( - &self, - key: ImageKey, - descriptor: ImageDescriptor, - data: SerializableImageData, - ) { - if let Err(e) = self.0.send(CrossProcessCompositorMessage::AddImage( - key, descriptor, data, - )) { - warn!("Error sending image update: {}", e); - } - } - - /// Perform an image resource update operation. - pub fn update_images(&self, updates: Vec) { - if let Err(e) = self - .0 - .send(CrossProcessCompositorMessage::UpdateImages(updates)) - { - warn!("error sending image updates: {}", e); - } - } - - pub fn remove_unused_font_resources( - &self, - keys: Vec, - instance_keys: Vec, - ) { - if keys.is_empty() && instance_keys.is_empty() { - return; - } - let _ = self.0.send(CrossProcessCompositorMessage::RemoveFonts( - keys, - instance_keys, - )); - } - - pub fn add_font_instance( - &self, - font_instance_key: FontInstanceKey, - font_key: FontKey, - size: f32, - flags: FontInstanceFlags, - ) { - let _x = self.0.send(CrossProcessCompositorMessage::AddFontInstance( - font_instance_key, - font_key, - size, - flags, - )); - } - - pub fn add_font(&self, font_key: FontKey, data: Arc, index: u32) { - let _ = self.0.send(CrossProcessCompositorMessage::AddFont( - font_key, data, index, - )); - } - - pub fn add_system_font(&self, font_key: FontKey, handle: NativeFontHandle) { - let _ = self.0.send(CrossProcessCompositorMessage::AddSystemFont( - font_key, handle, - )); - } - - pub fn fetch_font_keys( - &self, - number_of_font_keys: usize, - number_of_font_instance_keys: usize, - ) -> (Vec, Vec) { - let (sender, receiver) = ipc_channel::ipc::channel().expect("Could not create IPC channel"); - let _ = self.0.send(CrossProcessCompositorMessage::GenerateFontKeys( - number_of_font_keys, - number_of_font_instance_keys, - sender, - )); - receiver.recv().unwrap() - } -} - -/// This trait is used as a bridge between the different GL clients -/// in Servo that handles WebRender ExternalImages and the WebRender -/// ExternalImageHandler API. -// -/// This trait is used to notify lock/unlock messages and get the -/// required info that WR needs. -pub trait WebrenderExternalImageApi { - fn lock(&mut self, id: u64) -> (WebrenderImageSource, UntypedSize2D); - fn unlock(&mut self, id: u64); -} - -pub enum WebrenderImageSource<'a> { - TextureHandle(u32), - Raw(&'a [u8]), -} - -/// Type of Webrender External Image Handler. -pub enum WebrenderImageHandlerType { - WebGL, - Media, - WebGPU, -} - -/// List of Webrender external images to be shared among all external image -/// consumers (WebGL, Media, WebGPU). -/// It ensures that external image identifiers are unique. -#[derive(Default)] -pub struct WebrenderExternalImageRegistry { - /// Map of all generated external images. - external_images: HashMap, - /// Id generator for the next external image identifier. - next_image_id: u64, -} - -impl WebrenderExternalImageRegistry { - pub fn next_id(&mut self, handler_type: WebrenderImageHandlerType) -> ExternalImageId { - self.next_image_id += 1; - let key = ExternalImageId(self.next_image_id); - self.external_images.insert(key, handler_type); - key - } - - pub fn remove(&mut self, key: &ExternalImageId) { - self.external_images.remove(key); - } - - pub fn get(&self, key: &ExternalImageId) -> Option<&WebrenderImageHandlerType> { - self.external_images.get(key) - } -} - -/// WebRender External Image Handler implementation. -pub struct WebrenderExternalImageHandlers { - /// WebGL handler. - webgl_handler: Option>, - /// Media player handler. - media_handler: Option>, - /// WebGPU handler. - webgpu_handler: Option>, - /// Webrender external images. - external_images: Arc>, -} - -impl WebrenderExternalImageHandlers { - pub fn new() -> (Self, Arc>) { - let external_images = Arc::new(Mutex::new(WebrenderExternalImageRegistry::default())); - ( - Self { - webgl_handler: None, - media_handler: None, - webgpu_handler: None, - external_images: external_images.clone(), - }, - external_images, - ) - } - - pub fn set_handler( - &mut self, - handler: Box, - handler_type: WebrenderImageHandlerType, - ) { - match handler_type { - WebrenderImageHandlerType::WebGL => self.webgl_handler = Some(handler), - WebrenderImageHandlerType::Media => self.media_handler = Some(handler), - WebrenderImageHandlerType::WebGPU => self.webgpu_handler = Some(handler), - } - } -} - -impl ExternalImageHandler for WebrenderExternalImageHandlers { - /// 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. - fn lock(&mut self, key: ExternalImageId, _channel_index: u8) -> ExternalImage { - let external_images = self.external_images.lock().unwrap(); - let handler_type = external_images - .get(&key) - .expect("Tried to get unknown external image"); - match handler_type { - WebrenderImageHandlerType::WebGL => { - let (source, size) = self.webgl_handler.as_mut().unwrap().lock(key.0); - let texture_id = match source { - WebrenderImageSource::TextureHandle(b) => b, - _ => panic!("Wrong type"), - }; - ExternalImage { - uv: TexelRect::new(0.0, size.height as f32, size.width as f32, 0.0), - source: ExternalImageSource::NativeTexture(texture_id), - } - }, - WebrenderImageHandlerType::Media => { - let (source, size) = self.media_handler.as_mut().unwrap().lock(key.0); - let texture_id = match source { - WebrenderImageSource::TextureHandle(b) => b, - _ => panic!("Wrong type"), - }; - ExternalImage { - uv: TexelRect::new(0.0, size.height as f32, size.width as f32, 0.0), - source: ExternalImageSource::NativeTexture(texture_id), - } - }, - WebrenderImageHandlerType::WebGPU => { - let (source, size) = self.webgpu_handler.as_mut().unwrap().lock(key.0); - let buffer = match source { - WebrenderImageSource::Raw(b) => b, - _ => panic!("Wrong type"), - }; - ExternalImage { - uv: TexelRect::new(0.0, size.height as f32, size.width as f32, 0.0), - source: ExternalImageSource::RawData(buffer), - } - }, - } - } - - /// Unlock the external image. The WR should not read the image - /// content after this call. - fn unlock(&mut self, key: ExternalImageId, _channel_index: u8) { - let external_images = self.external_images.lock().unwrap(); - let handler_type = external_images - .get(&key) - .expect("Tried to get unknown external image"); - match handler_type { - WebrenderImageHandlerType::WebGL => self.webgl_handler.as_mut().unwrap().unlock(key.0), - WebrenderImageHandlerType::Media => self.media_handler.as_mut().unwrap().unlock(key.0), - WebrenderImageHandlerType::WebGPU => { - self.webgpu_handler.as_mut().unwrap().unlock(key.0) - }, - }; - } -} - -#[derive(Deserialize, Serialize)] -/// Serializable image updates that must be performed by WebRender. -pub enum ImageUpdate { - /// Register a new image. - AddImage(ImageKey, ImageDescriptor, SerializableImageData), - /// Delete a previously registered image registration. - DeleteImage(ImageKey), - /// Update an existing image registration. - UpdateImage(ImageKey, ImageDescriptor, SerializableImageData), -} - -#[derive(Debug, Deserialize, Serialize)] -/// Serialized `ImageData`. It contains IPC byte channel receiver to prevent from loading bytes too -/// slow. -pub enum SerializableImageData { - /// A simple series of bytes, provided by the embedding and owned by WebRender. - /// The format is stored out-of-band, currently in ImageDescriptor. - Raw(IpcSharedMemory), - /// An image owned by the embedding, and referenced by WebRender. This may - /// take the form of a texture or a heap-allocated buffer. - External(ExternalImageData), -} - -impl From for ImageData { - fn from(value: SerializableImageData) -> Self { - match value { - SerializableImageData::Raw(shared_memory) => ImageData::new(shared_memory.to_vec()), - SerializableImageData::External(image) => ImageData::External(image), - } - } -} - -/// A trait that exposes the embedding layer's `WebView` to the Servo renderer. -/// This is to prevent a dependency cycle between the renderer and the embedding -/// layer. -pub trait RendererWebView { - fn id(&self) -> WebViewId; - fn screen_geometry(&self) -> Option; -} diff --git a/components/webgpu/Cargo.toml b/components/webgpu/Cargo.toml index 029be8a5e76..f25f160b1b0 100644 --- a/components/webgpu/Cargo.toml +++ b/components/webgpu/Cargo.toml @@ -14,6 +14,7 @@ path = "lib.rs" [dependencies] arrayvec = { workspace = true, features = ["serde"] } base = { workspace = true } +compositing_traits = { workspace = true } euclid = { workspace = true } ipc-channel = { workspace = true } log = { workspace = true } @@ -23,7 +24,6 @@ servo_config = { path = "../config" } webgpu_traits = { workspace = true } webrender = { workspace = true } webrender_api = { workspace = true } -webrender_traits = { workspace = true } wgpu-core = { workspace = true, features = ["serde", "wgsl"] } wgpu-types = { workspace = true } diff --git a/components/webgpu/lib.rs b/components/webgpu/lib.rs index 1842258a9fb..ce09f77af49 100644 --- a/components/webgpu/lib.rs +++ b/components/webgpu/lib.rs @@ -16,10 +16,10 @@ mod wgpu_thread; use std::borrow::Cow; use std::sync::{Arc, Mutex}; +use compositing_traits::WebrenderExternalImageRegistry; use ipc_channel::ipc::{self, IpcReceiver}; use servo_config::pref; use webrender_api::DocumentId; -use webrender_traits::WebrenderExternalImageRegistry; pub mod swapchain; diff --git a/components/webgpu/swapchain.rs b/components/webgpu/swapchain.rs index 0245084e480..6d61540581b 100644 --- a/components/webgpu/swapchain.rs +++ b/components/webgpu/swapchain.rs @@ -8,6 +8,7 @@ use std::slice; use std::sync::{Arc, Mutex}; use arrayvec::ArrayVec; +use compositing_traits::{WebrenderExternalImageApi, WebrenderImageSource}; use euclid::default::Size2D; use ipc_channel::ipc::{IpcSender, IpcSharedMemory}; use log::{error, warn}; @@ -21,7 +22,6 @@ use webrender_api::{ DirtyRect, DocumentId, ExternalImageData, ExternalImageId, ExternalImageType, ImageData, ImageDescriptor, ImageDescriptorFlags, ImageFormat, ImageKey, }; -use webrender_traits::{WebrenderExternalImageApi, WebrenderImageSource}; use wgpu_core::device::HostMap; use wgpu_core::global::Global; use wgpu_core::id; diff --git a/components/webgpu/wgpu_thread.rs b/components/webgpu/wgpu_thread.rs index 93cf5a56bae..ce0303aaba7 100644 --- a/components/webgpu/wgpu_thread.rs +++ b/components/webgpu/wgpu_thread.rs @@ -10,6 +10,7 @@ use std::slice; use std::sync::{Arc, Mutex}; use base::id::PipelineId; +use compositing_traits::{WebrenderExternalImageRegistry, WebrenderImageHandlerType}; use ipc_channel::ipc::{IpcReceiver, IpcSender, IpcSharedMemory}; use log::{info, warn}; use servo_config::pref; @@ -20,7 +21,6 @@ use webgpu_traits::{ }; use webrender::{RenderApi, RenderApiSender}; use webrender_api::{DocumentId, ExternalImageId}; -use webrender_traits::{WebrenderExternalImageRegistry, WebrenderImageHandlerType}; use wgc::command::{ComputePass, ComputePassDescriptor, RenderPass}; use wgc::device::{DeviceDescriptor, ImplicitPipelineIds}; use wgc::id; diff --git a/python/servo/testing_commands.py b/python/servo/testing_commands.py index 53e0d27f9bc..8cc33e665b7 100644 --- a/python/servo/testing_commands.py +++ b/python/servo/testing_commands.py @@ -163,6 +163,7 @@ class MachCommands(CommandBase): "background_hang_monitor", "base", "compositing", + "compositing_traits", "constellation", "devtools", "fonts", @@ -178,7 +179,6 @@ class MachCommands(CommandBase): "servo_config", "servoshell", "stylo_config", - "webrender_traits", ] if not packages: packages = set(os.listdir(path.join(self.context.topdir, "tests", "unit"))) - set(['.DS_Store'])