Call prepare_pixels on the WebGL thread

This commit is contained in:
Anthony Ramine 2018-11-17 16:10:14 +01:00
parent 5f9e3d8bb9
commit ca62b5c318
5 changed files with 87 additions and 54 deletions

View file

@ -1045,25 +1045,40 @@ impl WebGLImpl {
WebGLCommand::TexImage2D { WebGLCommand::TexImage2D {
target, target,
level, level,
internal_format, effective_internal_format,
size, size,
format, format,
data_type, data_type,
effective_data_type,
unpacking_alignment, unpacking_alignment,
alpha_treatment,
y_axis_treatment,
tex_source,
ref receiver, ref receiver,
} => { } => {
let pixels = prepare_pixels(
format,
data_type,
size,
unpacking_alignment,
alpha_treatment,
y_axis_treatment,
tex_source,
receiver.recv().unwrap(),
);
ctx.gl() ctx.gl()
.pixel_store_i(gl::UNPACK_ALIGNMENT, unpacking_alignment as i32); .pixel_store_i(gl::UNPACK_ALIGNMENT, unpacking_alignment as i32);
ctx.gl().tex_image_2d( ctx.gl().tex_image_2d(
target, target,
level as i32, level as i32,
internal_format as i32, effective_internal_format as i32,
size.width as i32, size.width as i32,
size.height as i32, size.height as i32,
0, 0,
format, format.as_gl_constant(),
data_type, effective_data_type,
Some(&receiver.recv().unwrap()), Some(&pixels),
); );
}, },
WebGLCommand::TexSubImage2D { WebGLCommand::TexSubImage2D {
@ -1074,9 +1089,24 @@ impl WebGLImpl {
size, size,
format, format,
data_type, data_type,
effective_data_type,
unpacking_alignment, unpacking_alignment,
alpha_treatment,
y_axis_treatment,
tex_source,
ref receiver, ref receiver,
} => { } => {
let pixels = prepare_pixels(
format,
data_type,
size,
unpacking_alignment,
alpha_treatment,
y_axis_treatment,
tex_source,
receiver.recv().unwrap(),
);
ctx.gl() ctx.gl()
.pixel_store_i(gl::UNPACK_ALIGNMENT, unpacking_alignment as i32); .pixel_store_i(gl::UNPACK_ALIGNMENT, unpacking_alignment as i32);
ctx.gl().tex_sub_image_2d( ctx.gl().tex_sub_image_2d(
@ -1086,9 +1116,9 @@ impl WebGLImpl {
yoffset, yoffset,
size.width as i32, size.width as i32,
size.height as i32, size.height as i32,
format, format.as_gl_constant(),
data_type, effective_data_type,
&receiver.recv().unwrap(), &pixels,
); );
}, },
WebGLCommand::DrawingBufferWidth(ref sender) => sender WebGLCommand::DrawingBufferWidth(ref sender) => sender

View file

@ -275,11 +275,17 @@ pub enum WebGLCommand {
TexImage2D { TexImage2D {
target: u32, target: u32,
level: u32, level: u32,
internal_format: u32, // FIXME(nox): This should be computed on the WebGL thread.
effective_internal_format: u32,
size: Size2D<u32>, size: Size2D<u32>,
format: u32, format: TexFormat,
data_type: u32, data_type: TexDataType,
// FIXME(nox): This should be computed on the WebGL thread.
effective_data_type: u32,
unpacking_alignment: u32, unpacking_alignment: u32,
alpha_treatment: Option<AlphaTreatment>,
y_axis_treatment: YAxisTreatment,
tex_source: TexSource,
receiver: IpcBytesReceiver, receiver: IpcBytesReceiver,
}, },
TexSubImage2D { TexSubImage2D {
@ -288,9 +294,14 @@ pub enum WebGLCommand {
xoffset: i32, xoffset: i32,
yoffset: i32, yoffset: i32,
size: Size2D<u32>, size: Size2D<u32>,
format: u32, format: TexFormat,
data_type: u32, data_type: TexDataType,
// FIXME(nox): This should be computed on the WebGL thread.
effective_data_type: u32,
unpacking_alignment: u32, unpacking_alignment: u32,
alpha_treatment: Option<AlphaTreatment>,
y_axis_treatment: YAxisTreatment,
tex_source: TexSource,
receiver: IpcBytesReceiver, receiver: IpcBytesReceiver,
}, },
DrawingBufferWidth(WebGLSender<i32>), DrawingBufferWidth(WebGLSender<i32>),
@ -671,7 +682,8 @@ pub fn is_gles() -> bool {
macro_rules! gl_enums { macro_rules! gl_enums {
($(pub enum $name:ident { $($variant:ident = $mod:ident::$constant:ident,)+ })*) => { ($(pub enum $name:ident { $($variant:ident = $mod:ident::$constant:ident,)+ })*) => {
$( $(
#[derive(Clone, Copy, Debug, Eq, Hash, MallocSizeOf, PartialEq)] #[derive(Clone, Copy, Debug, Deserialize, Eq, Hash, MallocSizeOf)]
#[derive(PartialEq, Serialize)]
#[repr(u32)] #[repr(u32)]
pub enum $name { $($variant = $mod::$constant,)+ } pub enum $name { $($variant = $mod::$constant,)+ }
@ -755,19 +767,19 @@ impl TexDataType {
} }
} }
#[derive(Clone, Copy, Debug, Eq, Hash, MallocSizeOf, PartialEq)] #[derive(Clone, Copy, Debug, Deserialize, Eq, Hash, MallocSizeOf, PartialEq, Serialize)]
pub enum AlphaTreatment { pub enum AlphaTreatment {
Premultiply, Premultiply,
Unmultiply, Unmultiply,
} }
#[derive(Clone, Copy, Debug, Eq, Hash, MallocSizeOf, PartialEq)] #[derive(Clone, Copy, Debug, Deserialize, Eq, Hash, MallocSizeOf, PartialEq, Serialize)]
pub enum YAxisTreatment { pub enum YAxisTreatment {
AsIs, AsIs,
Flipped, Flipped,
} }
#[derive(Clone, Copy, Debug, Eq, Hash, MallocSizeOf, PartialEq)] #[derive(Clone, Copy, Debug, Deserialize, Eq, Hash, MallocSizeOf, PartialEq, Serialize)]
pub enum TexSource { pub enum TexSource {
FromHtmlElement, FromHtmlElement,
FromArray, FromArray,

View file

@ -89,7 +89,7 @@ script_layout_interface = {path = "../script_layout_interface"}
script_plugins = {path = "../script_plugins"} script_plugins = {path = "../script_plugins"}
script_traits = {path = "../script_traits"} script_traits = {path = "../script_traits"}
selectors = { path = "../selectors" } selectors = { path = "../selectors" }
serde = "1.0" serde = {version = "1", features = ["derive"]}
serde_bytes = "0.10" serde_bytes = "0.10"
servo_allocator = {path = "../allocator"} servo_allocator = {path = "../allocator"}
servo_arc = {path = "../servo_arc"} servo_arc = {path = "../servo_arc"}

View file

@ -6,7 +6,7 @@
use backtrace::Backtrace; use backtrace::Backtrace;
use canvas_traits::webgl::WebGLError::*; use canvas_traits::webgl::WebGLError::*;
use canvas_traits::webgl::{ use canvas_traits::webgl::{
self, webgl_channel, AlphaTreatment, DOMToTextureCommand, Parameter, TexDataType, TexFormat, webgl_channel, AlphaTreatment, DOMToTextureCommand, Parameter, TexDataType, TexFormat,
TexParameter, TexSource, WebGLCommand, WebGLCommandBacktrace, WebGLContextShareMode, TexParameter, TexSource, WebGLCommand, WebGLCommandBacktrace, WebGLContextShareMode,
WebGLError, WebGLFramebufferBindingRequest, WebGLMsg, WebGLMsgSender, WebGLProgramId, WebGLError, WebGLFramebufferBindingRequest, WebGLMsg, WebGLMsgSender, WebGLProgramId,
WebGLResult, WebGLSLVersion, WebGLSender, WebGLVersion, WebVRCommand, YAxisTreatment, WebGLResult, WebGLSLVersion, WebGLSender, WebGLVersion, WebVRCommand, YAxisTreatment,
@ -643,7 +643,7 @@ impl WebGLRenderingContext {
texture: &WebGLTexture, texture: &WebGLTexture,
target: TexImageTarget, target: TexImageTarget,
data_type: TexDataType, data_type: TexDataType,
internal_format: TexFormat, format: TexFormat,
level: u32, level: u32,
_border: u32, _border: u32,
unpacking_alignment: u32, unpacking_alignment: u32,
@ -658,7 +658,7 @@ impl WebGLRenderingContext {
pixels.size.width, pixels.size.width,
pixels.size.height, pixels.size.height,
1, 1,
internal_format, format,
level, level,
Some(data_type) Some(data_type)
) )
@ -679,36 +679,30 @@ impl WebGLRenderingContext {
YAxisTreatment::AsIs YAxisTreatment::AsIs
}; };
let buff = webgl::prepare_pixels( let effective_internal_format = self
internal_format,
data_type,
pixels.size,
unpacking_alignment,
alpha_treatment,
y_axis_treatment,
tex_source,
pixels.data,
);
let format = internal_format.as_gl_constant();
let data_type = data_type.as_gl_constant();
let internal_format = self
.extension_manager .extension_manager
.get_effective_tex_internal_format(format, data_type); .get_effective_tex_internal_format(format.as_gl_constant(), data_type.as_gl_constant());
let effective_data_type = self
.extension_manager
.effective_type(data_type.as_gl_constant());
// TODO(emilio): convert colorspace if requested // TODO(emilio): convert colorspace if requested
let (sender, receiver) = ipc::bytes_channel().unwrap(); let (sender, receiver) = ipc::bytes_channel().unwrap();
self.send_command(WebGLCommand::TexImage2D { self.send_command(WebGLCommand::TexImage2D {
target: target.as_gl_constant(), target: target.as_gl_constant(),
level, level,
internal_format, effective_internal_format,
size: pixels.size, size: pixels.size,
format, format,
data_type: self.extension_manager.effective_type(data_type), data_type,
effective_data_type,
unpacking_alignment, unpacking_alignment,
alpha_treatment,
y_axis_treatment,
tex_source,
receiver, receiver,
}); });
sender.send(&buff).unwrap(); sender.send(&pixels.data).unwrap();
if let Some(fb) = self.bound_framebuffer.get() { if let Some(fb) = self.bound_framebuffer.get() {
fb.invalidate_texture(&*texture); fb.invalidate_texture(&*texture);
@ -765,16 +759,9 @@ impl WebGLRenderingContext {
YAxisTreatment::AsIs YAxisTreatment::AsIs
}; };
let buff = webgl::prepare_pixels( let effective_data_type = self
format, .extension_manager
data_type, .effective_type(data_type.as_gl_constant());
pixels.size,
unpacking_alignment,
alpha_treatment,
y_axis_treatment,
tex_source,
pixels.data,
);
// TODO(emilio): convert colorspace if requested // TODO(emilio): convert colorspace if requested
let (sender, receiver) = ipc::bytes_channel().unwrap(); let (sender, receiver) = ipc::bytes_channel().unwrap();
@ -784,14 +771,16 @@ impl WebGLRenderingContext {
xoffset, xoffset,
yoffset, yoffset,
size: pixels.size, size: pixels.size,
format: format.as_gl_constant(), format,
data_type: self data_type,
.extension_manager effective_data_type,
.effective_type(data_type.as_gl_constant()),
unpacking_alignment, unpacking_alignment,
alpha_treatment,
y_axis_treatment,
tex_source,
receiver, receiver,
}); });
sender.send(&buff).unwrap(); sender.send(&pixels.data).unwrap();
} }
fn get_gl_extensions(&self) -> String { fn get_gl_extensions(&self) -> String {

View file

@ -46,6 +46,8 @@ extern crate malloc_size_of_derive;
#[macro_use] #[macro_use]
extern crate profile_traits; extern crate profile_traits;
#[macro_use] #[macro_use]
extern crate serde;
#[macro_use]
extern crate servo_atoms; extern crate servo_atoms;
#[macro_use] #[macro_use]
extern crate style; extern crate style;