mirror of
https://github.com/servo/servo.git
synced 2025-10-15 07:50:20 +01:00
Instead of exposing many different kinds of messages to the compositor that are routed through the constellation, expose a single message type which can be sent across IPC channels. In addition, this IPC channel and the route to the crossbeam channel with the compositor is created along with the `CompositorProxy`, simplifying what needs to be passed around during pipeline initialization. Previously, some image updates (from video) were sent over IPC with a special serialization routine and some were sent via crossbeam channels (canvas). Now all updates go over the IPC channel `IpcSharedMemory` is used to avoid serialization penalties. This should improve performance and reduce copies for video, but add a memory copy overhead for canvas. This will improve in the future when canvas renders directly into a texture. All-in-all this is a simplification which opens the path toward having a standard compositor API and reduces the number of duplicate messages and proxying that had to happen in libservo. Signed-off-by: Martin Robinson <mrobinson@igalia.com>
This commit is contained in:
parent
30cbf01280
commit
9195344b75
28 changed files with 547 additions and 800 deletions
|
@ -28,15 +28,13 @@ pub use base::id::TopLevelBrowsingContextId;
|
|||
use base::id::{PipelineNamespace, PipelineNamespaceId};
|
||||
use bluetooth::BluetoothThreadFactory;
|
||||
use bluetooth_traits::BluetoothRequest;
|
||||
use canvas::canvas_paint_thread::{self, CanvasPaintThread};
|
||||
use canvas::canvas_paint_thread::CanvasPaintThread;
|
||||
use canvas::WebGLComm;
|
||||
use canvas_traits::webgl::WebGLThreads;
|
||||
use compositing::webview::UnknownWebView;
|
||||
use compositing::windowing::{EmbedderEvent, EmbedderMethods, WindowMethods};
|
||||
use compositing::{CompositeTarget, IOCompositor, InitialCompositorState, ShutdownState};
|
||||
use compositing_traits::{
|
||||
CompositorMsg, CompositorProxy, CompositorReceiver, ConstellationMsg, ForwardedToCompositorMsg,
|
||||
};
|
||||
use compositing_traits::{CompositorMsg, CompositorProxy, CompositorReceiver, ConstellationMsg};
|
||||
#[cfg(all(
|
||||
not(target_os = "windows"),
|
||||
not(target_os = "ios"),
|
||||
|
@ -66,7 +64,8 @@ use fonts::SystemFontService;
|
|||
use gaol::sandbox::{ChildSandbox, ChildSandboxMethods};
|
||||
pub use gleam::gl;
|
||||
use gleam::gl::RENDERER;
|
||||
use ipc_channel::ipc::{self, IpcSender, IpcSharedMemory};
|
||||
use ipc_channel::ipc::{self, IpcSender};
|
||||
use ipc_channel::router::ROUTER;
|
||||
#[cfg(feature = "layout_2013")]
|
||||
pub use layout_thread_2013;
|
||||
use log::{error, trace, warn, Log, Metadata, Record};
|
||||
|
@ -91,13 +90,10 @@ use surfman::{GLApi, GLVersion};
|
|||
use surfman::{NativeConnection, NativeContext};
|
||||
use webgpu::swapchain::WGPUImageMap;
|
||||
use webrender::{RenderApiSender, ShaderPrecacheFlags, UploadMethod, ONE_TIME_USAGE_HINT};
|
||||
use webrender_api::{
|
||||
ColorF, DocumentId, FontInstanceFlags, FontInstanceKey, FontKey, FramePublishId, ImageKey,
|
||||
NativeFontHandle,
|
||||
};
|
||||
use webrender_api::{ColorF, DocumentId, FramePublishId};
|
||||
use webrender_traits::{
|
||||
CanvasToCompositorMsg, FontToCompositorMsg, ImageUpdate, RenderingContext, WebRenderFontApi,
|
||||
WebrenderExternalImageHandlers, WebrenderExternalImageRegistry, WebrenderImageHandlerType,
|
||||
CrossProcessCompositorApi, RenderingContext, WebrenderExternalImageHandlers,
|
||||
WebrenderExternalImageRegistry, WebrenderImageHandlerType,
|
||||
};
|
||||
pub use {
|
||||
background_hang_monitor, base, bluetooth, bluetooth_traits, canvas, canvas_traits, compositing,
|
||||
|
@ -979,9 +975,24 @@ fn create_compositor_channel(
|
|||
event_loop_waker: Box<dyn EventLoopWaker>,
|
||||
) -> (CompositorProxy, CompositorReceiver) {
|
||||
let (sender, receiver) = unbounded();
|
||||
|
||||
let (compositor_ipc_sender, compositor_ipc_receiver) =
|
||||
ipc::channel().expect("ipc channel failure");
|
||||
let sender_clone = sender.clone();
|
||||
ROUTER.add_route(
|
||||
compositor_ipc_receiver.to_opaque(),
|
||||
Box::new(move |message| {
|
||||
let _ = sender_clone.send(CompositorMsg::CrossProcess(
|
||||
message.to().expect("Could not convert Compositor message"),
|
||||
));
|
||||
}),
|
||||
);
|
||||
let cross_process_compositor_api = CrossProcessCompositorApi(compositor_ipc_sender);
|
||||
|
||||
(
|
||||
CompositorProxy {
|
||||
sender,
|
||||
cross_process_compositor_api,
|
||||
event_loop_waker,
|
||||
},
|
||||
CompositorReceiver { receiver },
|
||||
|
@ -1043,14 +1054,11 @@ fn create_constellation(
|
|||
);
|
||||
|
||||
let system_font_service = Arc::new(
|
||||
SystemFontService::spawn(Box::new(WebRenderFontApiCompositorProxy(
|
||||
compositor_proxy.clone(),
|
||||
)))
|
||||
.to_proxy(),
|
||||
SystemFontService::spawn(compositor_proxy.cross_process_compositor_api.clone()).to_proxy(),
|
||||
);
|
||||
|
||||
let (canvas_create_sender, canvas_ipc_sender) = CanvasPaintThread::start(
|
||||
Box::new(CanvasWebrenderApi(compositor_proxy.clone())),
|
||||
compositor_proxy.cross_process_compositor_api.clone(),
|
||||
system_font_service.clone(),
|
||||
public_resource_threads.clone(),
|
||||
);
|
||||
|
@ -1094,82 +1102,6 @@ fn create_constellation(
|
|||
)
|
||||
}
|
||||
|
||||
struct WebRenderFontApiCompositorProxy(CompositorProxy);
|
||||
|
||||
impl WebRenderFontApi for WebRenderFontApiCompositorProxy {
|
||||
fn add_font_instance(
|
||||
&self,
|
||||
font_instance_key: FontInstanceKey,
|
||||
font_key: FontKey,
|
||||
size: f32,
|
||||
flags: FontInstanceFlags,
|
||||
) {
|
||||
self.0.send(CompositorMsg::Forwarded(
|
||||
ForwardedToCompositorMsg::SystemFontService(FontToCompositorMsg::AddFontInstance(
|
||||
font_instance_key,
|
||||
font_key,
|
||||
size,
|
||||
flags,
|
||||
)),
|
||||
));
|
||||
}
|
||||
|
||||
fn add_font(&self, font_key: FontKey, data: Arc<IpcSharedMemory>, index: u32) {
|
||||
self.0.send(CompositorMsg::Forwarded(
|
||||
ForwardedToCompositorMsg::SystemFontService(FontToCompositorMsg::AddFont(
|
||||
font_key, index, data,
|
||||
)),
|
||||
));
|
||||
}
|
||||
|
||||
fn add_system_font(&self, font_key: FontKey, handle: NativeFontHandle) {
|
||||
self.0.send(CompositorMsg::Forwarded(
|
||||
ForwardedToCompositorMsg::SystemFontService(FontToCompositorMsg::AddSystemFont(
|
||||
font_key, handle,
|
||||
)),
|
||||
));
|
||||
}
|
||||
|
||||
fn fetch_font_keys(
|
||||
&self,
|
||||
number_of_font_keys: usize,
|
||||
number_of_font_instance_keys: usize,
|
||||
) -> (Vec<FontKey>, Vec<FontInstanceKey>) {
|
||||
let (sender, receiver) = unbounded();
|
||||
self.0.send(CompositorMsg::Forwarded(
|
||||
ForwardedToCompositorMsg::SystemFontService(FontToCompositorMsg::GenerateKeys(
|
||||
number_of_font_keys,
|
||||
number_of_font_instance_keys,
|
||||
sender,
|
||||
)),
|
||||
));
|
||||
receiver.recv().unwrap()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone)]
|
||||
struct CanvasWebrenderApi(CompositorProxy);
|
||||
|
||||
impl canvas_paint_thread::WebrenderApi for CanvasWebrenderApi {
|
||||
fn generate_key(&self) -> Option<ImageKey> {
|
||||
let (sender, receiver) = unbounded();
|
||||
self.0
|
||||
.send(CompositorMsg::Forwarded(ForwardedToCompositorMsg::Canvas(
|
||||
CanvasToCompositorMsg::GenerateKey(sender),
|
||||
)));
|
||||
receiver.recv().ok()
|
||||
}
|
||||
fn update_images(&self, updates: Vec<ImageUpdate>) {
|
||||
self.0
|
||||
.send(CompositorMsg::Forwarded(ForwardedToCompositorMsg::Canvas(
|
||||
CanvasToCompositorMsg::UpdateImages(updates),
|
||||
)));
|
||||
}
|
||||
fn clone(&self) -> Box<dyn canvas_paint_thread::WebrenderApi> {
|
||||
Box::new(<Self as Clone>::clone(self))
|
||||
}
|
||||
}
|
||||
|
||||
// A logger that logs to two downstream loggers.
|
||||
// This should probably be in the log crate.
|
||||
struct BothLogger<Log1, Log2>(Log1, Log2);
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue