mirror of
https://github.com/servo/servo.git
synced 2025-08-06 14:10:11 +01:00
gfx: Use pipes to transfer layer buffers between the render supervisor function and the render callback
This commit is contained in:
parent
dbcb85b724
commit
a338c76bc6
2 changed files with 43 additions and 20 deletions
|
@ -5,6 +5,7 @@ use opts::Opts;
|
||||||
use azure::AzFloat;
|
use azure::AzFloat;
|
||||||
use azure::azure_hl::{B8G8R8A8, DrawTarget};
|
use azure::azure_hl::{B8G8R8A8, DrawTarget};
|
||||||
use core::libc::c_int;
|
use core::libc::c_int;
|
||||||
|
use core::pipes::Chan;
|
||||||
use geom::matrix2d::Matrix2D;
|
use geom::matrix2d::Matrix2D;
|
||||||
use geom::point::Point2D;
|
use geom::point::Point2D;
|
||||||
use geom::rect::Rect;
|
use geom::rect::Rect;
|
||||||
|
@ -17,6 +18,8 @@ pub struct RenderLayer {
|
||||||
size: Size2D<uint>
|
size: Size2D<uint>
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type RenderFn = &fn(layer: &RenderLayer, buffer: LayerBuffer, return_buffer: Chan<LayerBuffer>);
|
||||||
|
|
||||||
/// Given a layer and a buffer, either reuses the buffer (if it's of the right size and format)
|
/// Given a layer and a buffer, either reuses the buffer (if it's of the right size and format)
|
||||||
/// or creates a new buffer (if it's not of the appropriate size and format) and invokes the
|
/// or creates a new buffer (if it's not of the appropriate size and format) and invokes the
|
||||||
/// given callback with the render layer and the buffer. Returns the resulting layer buffer (which
|
/// given callback with the render layer and the buffer. Returns the resulting layer buffer (which
|
||||||
|
@ -24,11 +27,11 @@ pub struct RenderLayer {
|
||||||
pub fn render_layers(layer: &RenderLayer,
|
pub fn render_layers(layer: &RenderLayer,
|
||||||
buffer_set: LayerBufferSet,
|
buffer_set: LayerBufferSet,
|
||||||
opts: &Opts,
|
opts: &Opts,
|
||||||
f: &fn(layer: &RenderLayer, buffer: &LayerBuffer) -> bool) -> LayerBufferSet {
|
f: RenderFn) -> LayerBufferSet {
|
||||||
let mut buffers = match move buffer_set { LayerBufferSet { buffers: move b } => move b };
|
let mut buffers = match move buffer_set { LayerBufferSet { buffers: move b } => move b };
|
||||||
|
|
||||||
// FIXME: Try not to create a new array here.
|
// FIXME: Try not to create a new array here.
|
||||||
let new_buffers = dvec::DVec();
|
let new_buffer_ports = dvec::DVec();
|
||||||
|
|
||||||
// Divide up the layer into tiles.
|
// Divide up the layer into tiles.
|
||||||
let mut y = 0;
|
let mut y = 0;
|
||||||
|
@ -100,14 +103,26 @@ pub fn render_layers(layer: &RenderLayer,
|
||||||
};
|
};
|
||||||
//}
|
//}
|
||||||
|
|
||||||
let _ = f(layer, &buffer);
|
// Create a port and channel pair to receive the new buffer.
|
||||||
new_buffers.push(move buffer);
|
let (new_buffer_chan, new_buffer_port) = pipes::stream();
|
||||||
|
|
||||||
|
// Send the buffer to the child.
|
||||||
|
f(layer, move buffer, move new_buffer_chan);
|
||||||
|
|
||||||
|
// Enqueue the port.
|
||||||
|
new_buffer_ports.push(move new_buffer_port);
|
||||||
|
|
||||||
x += TILE_SIZE;
|
x += TILE_SIZE;
|
||||||
}
|
}
|
||||||
y += TILE_SIZE;
|
y += TILE_SIZE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
debug!("servo::gfx::render_layers: waiting on ports...");
|
||||||
|
let new_buffers = dvec::DVec();
|
||||||
|
for new_buffer_ports.each |new_buffer_port| {
|
||||||
|
new_buffers.push(new_buffer_port.recv());
|
||||||
|
}
|
||||||
|
|
||||||
return LayerBufferSet { buffers: move dvec::unwrap(move new_buffers) };
|
return LayerBufferSet { buffers: move dvec::unwrap(move new_buffers) };
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -87,25 +87,33 @@ impl<C: Compositor Send> Renderer<C> {
|
||||||
let layer_buffer_set = layer_buffer_set_cell.take();
|
let layer_buffer_set = layer_buffer_set_cell.take();
|
||||||
let layer_buffer_set_channel = layer_buffer_set_channel_cell.take();
|
let layer_buffer_set_channel = layer_buffer_set_channel_cell.take();
|
||||||
|
|
||||||
let layer_buffer_set = for render_layers(&render_layer,
|
let layer_buffer_set = do render_layers(&render_layer,
|
||||||
move layer_buffer_set,
|
move layer_buffer_set,
|
||||||
&self.opts)
|
&self.opts)
|
||||||
|render_layer, layer_buffer| {
|
|render_layer, layer_buffer, buffer_chan| {
|
||||||
let ctx = RenderContext {
|
{
|
||||||
canvas: layer_buffer,
|
// Build the render context.
|
||||||
font_ctx: self.font_ctx,
|
let ctx = RenderContext {
|
||||||
opts: &self.opts
|
canvas: &layer_buffer,
|
||||||
};
|
font_ctx: self.font_ctx,
|
||||||
|
opts: &self.opts
|
||||||
|
};
|
||||||
|
|
||||||
// Apply the translation to render the tile we want.
|
// Apply the translation to render the tile we want.
|
||||||
let matrix: Matrix2D<AzFloat> = Matrix2D::identity();
|
let matrix: Matrix2D<AzFloat> = Matrix2D::identity();
|
||||||
let matrix = matrix.translate(&-(layer_buffer.rect.origin.x as AzFloat),
|
let matrix = matrix.translate(&-(layer_buffer.rect.origin.x as AzFloat),
|
||||||
&-(layer_buffer.rect.origin.y as AzFloat));
|
&-(layer_buffer.rect.origin.y as AzFloat));
|
||||||
layer_buffer.draw_target.set_transform(&matrix);
|
layer_buffer.draw_target.set_transform(&matrix);
|
||||||
|
|
||||||
ctx.clear();
|
// Clear the buffer.
|
||||||
|
ctx.clear();
|
||||||
|
|
||||||
render_layer.display_list.draw_into_context(&ctx);
|
// Draw the display list.
|
||||||
|
render_layer.display_list.draw_into_context(&ctx);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Send back the buffer.
|
||||||
|
buffer_chan.send(move layer_buffer);
|
||||||
};
|
};
|
||||||
|
|
||||||
#debug("renderer: returning surface");
|
#debug("renderer: returning surface");
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue