Skip to content
Permalink
Browse files

webgl: finish, flush, detachShader, generateMipmap, Uniform1i

  • Loading branch information...
cbrewster committed Mar 27, 2016
1 parent d0f692b commit 3fd7634f545871603577d83a08950ab6f7026f1c
@@ -266,6 +266,14 @@ macro_rules! make_nonzero_dimension_setter(
/// For use on non-jsmanaged types
/// Use #[derive(JSTraceable)] on JS managed types
macro_rules! no_jsmanaged_fields(
([$ty:ident; $count:expr]) => (
impl $crate::dom::bindings::trace::JSTraceable for [$ty; $count] {
#[inline]
fn trace(&self, _: *mut ::js::jsapi::JSTracer) {
// Do nothing
}
}
);
($($ty:ident),+) => (
$(
impl $crate::dom::bindings::trace::JSTraceable for $ty {
@@ -94,7 +94,10 @@ impl WebGLProgram {
let shader_slot = match shader.gl_type() {
constants::FRAGMENT_SHADER => &self.fragment_shader,
constants::VERTEX_SHADER => &self.vertex_shader,
_ => return Err(WebGLError::InvalidOperation),
_ => {
error!("detachShader: Unexpected shader type");
return Err(WebGLError::InvalidValue);
}
};

// TODO(emilio): Differentiate between same shader already assigned and other previous
@@ -110,6 +113,32 @@ impl WebGLProgram {
Ok(())
}

/// glDetachShader
pub fn detach_shader(&self, shader: &WebGLShader) -> WebGLResult<()> {
let shader_slot = match shader.gl_type() {
constants::FRAGMENT_SHADER => &self.fragment_shader,
constants::VERTEX_SHADER => &self.vertex_shader,
_ => {
error!("detachShader: Unexpected shader type");
return Err(WebGLError::InvalidValue);
}
};

match shader_slot.get() {
Some(ref attached_shader) if attached_shader.id() != shader.id() =>
return Err(WebGLError::InvalidOperation),
None =>
return Err(WebGLError::InvalidOperation),
_ => {}
}

shader_slot.set(None);

self.renderer.send(CanvasMsg::WebGL(WebGLCommand::DetachShader(self.id, shader.id()))).unwrap();

Ok(())
}

/// glBindAttribLocation
pub fn bind_attrib_location(&self, index: u32, name: DOMString) -> WebGLResult<()> {
if name.len() > MAX_UNIFORM_AND_ATTRIBUTE_LEN {
@@ -181,6 +181,22 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
Root::from_ref(&*self.canvas)
}

// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.11
fn Flush(&self) {
self.ipc_renderer
.send(CanvasMsg::WebGL(WebGLCommand::Flush))
.unwrap();
}

// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.11
fn Finish(&self) {
let (sender, receiver) = ipc::channel().unwrap();
self.ipc_renderer
.send(CanvasMsg::WebGL(WebGLCommand::Finish(sender)))
.unwrap();
receiver.recv().unwrap()
}

// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.1
fn DrawingBufferWidth(&self) -> i32 {
let (sender, receiver) = ipc::channel().unwrap();
@@ -331,6 +347,15 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
}
}

// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.9
fn DetachShader(&self, program: Option<&WebGLProgram>, shader: Option<&WebGLShader>) {
if let Some(program) = program {
if let Some(shader) = shader {
handle_potential_webgl_error!(self, program.detach_shader(shader));
}
}
}

// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.9
fn BindAttribLocation(&self, program: Option<&WebGLProgram>,
index: u32, name: DOMString) {
@@ -414,6 +439,21 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
}
}

// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.8
fn GenerateMipmap(&self, target: u32) {
let slot = match target {
constants::TEXTURE_2D => &self.bound_texture_2d,
constants::TEXTURE_CUBE_MAP => &self.bound_texture_cube_map,

_ => return self.webgl_error(InvalidEnum),
};

match slot.get() {
Some(texture) => handle_potential_webgl_error!(self, texture.generate_mipmap()),
None => self.webgl_error(InvalidOperation)
}
}

#[allow(unsafe_code)]
// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.5
fn BufferData(&self, _cx: *mut JSContext, target: u32, data: Option<*mut JSObject>, usage: u32) {
@@ -949,6 +989,25 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
.unwrap()
}

// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.10
fn Uniform1i(&self,
uniform: Option<&WebGLUniformLocation>,
val: i32) {
let uniform = match uniform {
Some(uniform) => uniform,
None => return,
};

match self.current_program.get() {
Some(ref program) if program.id() == uniform.program_id() => {},
_ => return self.webgl_error(InvalidOperation),
};

self.ipc_renderer
.send(CanvasMsg::WebGL(WebGLCommand::Uniform1i(uniform.id(), val)))
.unwrap()
}

// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.10
fn Uniform1fv(&self,
uniform: Option<&WebGLUniformLocation>,
@@ -1107,7 +1166,7 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
internal_format: u32,
format: u32,
data_type: u32,
source: Option<ImageDataOrHTMLImageElementOrHTMLCanvasElementOrHTMLVideoElement >) {
source: Option<ImageDataOrHTMLImageElementOrHTMLCanvasElementOrHTMLVideoElement>) {
let texture = match target {
constants::TEXTURE_2D => self.bound_texture_2d.get(),
constants::TEXTURE_CUBE_MAP => self.bound_texture_cube_map.get(),
@@ -1169,11 +1228,22 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
=> unimplemented!(),
};

if size.width < 0 || size.height < 0 || level < 0 {
self.webgl_error(WebGLError::InvalidOperation);
}

// TODO(emilio): Invert axis, convert colorspace, premultiply alpha if requested
let msg = WebGLCommand::TexImage2D(target, level, internal_format as i32,
size.width, size.height,
format, data_type, pixels);

// depth is always 1 when coming from html elements
handle_potential_webgl_error!(self, texture.unwrap().initialize(size.width as u32,
size.height as u32,
1,
internal_format,
level as u32));

self.ipc_renderer
.send(CanvasMsg::WebGL(msg))
.unwrap()
@@ -99,7 +99,7 @@ impl WebGLShader {
let validator = ShaderValidator::for_webgl(self.gl_type,
SHADER_OUTPUT_FORMAT,
&BuiltInResources::default()).unwrap();
match validator.compile_and_translate(&[source.as_bytes()]) {
match validator.compile_and_translate(&[source]) {
Ok(translated_source) => {
// NOTE: At this point we should be pretty sure that the compilation in the paint thread
// will succeed.
Oops, something went wrong.

0 comments on commit 3fd7634

Please sign in to comment.
You can’t perform that action at this time.