mirror of
https://github.com/servo/servo.git
synced 2025-07-31 19:20:22 +01:00
Add support for WebGL2 uniform matrix operations
Adds support for the `uniformMatrix[234]x[234]fv` WebGL2 functions. See: https://www.khronos.org/registry/webgl/specs/latest/2.0/#3.7.8
This commit is contained in:
parent
0650fc3199
commit
7d5048f885
10 changed files with 398 additions and 219 deletions
|
@ -50,7 +50,7 @@ use js::jsapi::{JSObject, Type};
|
|||
use js::jsval::{BooleanValue, DoubleValue, Int32Value, UInt32Value};
|
||||
use js::jsval::{JSVal, NullValue, ObjectValue, UndefinedValue};
|
||||
use js::rust::CustomAutoRooterGuard;
|
||||
use js::typedarray::{ArrayBufferView, CreateWith, Uint32, Uint32Array};
|
||||
use js::typedarray::{ArrayBufferView, CreateWith, Float32, Uint32, Uint32Array};
|
||||
use script_layout_interface::HTMLCanvasDataSource;
|
||||
use std::cell::Cell;
|
||||
use std::cmp;
|
||||
|
@ -1744,8 +1744,11 @@ impl WebGL2RenderingContextMethods for WebGL2RenderingContext {
|
|||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
v: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.base.UniformMatrix2fv(location, transpose, v)
|
||||
self.base
|
||||
.UniformMatrix2fv(location, transpose, v, src_offset, src_length)
|
||||
}
|
||||
|
||||
/// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.10
|
||||
|
@ -1754,8 +1757,11 @@ impl WebGL2RenderingContextMethods for WebGL2RenderingContext {
|
|||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
v: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.base.UniformMatrix3fv(location, transpose, v)
|
||||
self.base
|
||||
.UniformMatrix3fv(location, transpose, v, src_offset, src_length)
|
||||
}
|
||||
|
||||
/// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.10
|
||||
|
@ -1764,8 +1770,179 @@ impl WebGL2RenderingContextMethods for WebGL2RenderingContext {
|
|||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
v: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.base.UniformMatrix4fv(location, transpose, v)
|
||||
self.base
|
||||
.UniformMatrix4fv(location, transpose, v, src_offset, src_length)
|
||||
}
|
||||
|
||||
/// https://www.khronos.org/registry/webgl/specs/latest/2.0/#3.7.8
|
||||
fn UniformMatrix3x2fv(
|
||||
&self,
|
||||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
val: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.base.with_location(location, |location| {
|
||||
match location.type_() {
|
||||
constants::FLOAT_MAT3x2 => {},
|
||||
_ => return Err(InvalidOperation),
|
||||
}
|
||||
let val = self.base.uniform_matrix_section(
|
||||
val,
|
||||
src_offset,
|
||||
src_length,
|
||||
transpose,
|
||||
3 * 2,
|
||||
location,
|
||||
)?;
|
||||
self.base
|
||||
.send_command(WebGLCommand::UniformMatrix3x2fv(location.id(), val));
|
||||
Ok(())
|
||||
});
|
||||
}
|
||||
|
||||
/// https://www.khronos.org/registry/webgl/specs/latest/2.0/#3.7.8
|
||||
fn UniformMatrix4x2fv(
|
||||
&self,
|
||||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
val: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.base.with_location(location, |location| {
|
||||
match location.type_() {
|
||||
constants::FLOAT_MAT4x2 => {},
|
||||
_ => return Err(InvalidOperation),
|
||||
}
|
||||
let val = self.base.uniform_matrix_section(
|
||||
val,
|
||||
src_offset,
|
||||
src_length,
|
||||
transpose,
|
||||
4 * 2,
|
||||
location,
|
||||
)?;
|
||||
self.base
|
||||
.send_command(WebGLCommand::UniformMatrix4x2fv(location.id(), val));
|
||||
Ok(())
|
||||
});
|
||||
}
|
||||
|
||||
/// https://www.khronos.org/registry/webgl/specs/latest/2.0/#3.7.8
|
||||
fn UniformMatrix2x3fv(
|
||||
&self,
|
||||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
val: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.base.with_location(location, |location| {
|
||||
match location.type_() {
|
||||
constants::FLOAT_MAT2x3 => {},
|
||||
_ => return Err(InvalidOperation),
|
||||
}
|
||||
let val = self.base.uniform_matrix_section(
|
||||
val,
|
||||
src_offset,
|
||||
src_length,
|
||||
transpose,
|
||||
2 * 3,
|
||||
location,
|
||||
)?;
|
||||
self.base
|
||||
.send_command(WebGLCommand::UniformMatrix2x3fv(location.id(), val));
|
||||
Ok(())
|
||||
});
|
||||
}
|
||||
|
||||
/// https://www.khronos.org/registry/webgl/specs/latest/2.0/#3.7.8
|
||||
fn UniformMatrix4x3fv(
|
||||
&self,
|
||||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
val: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.base.with_location(location, |location| {
|
||||
match location.type_() {
|
||||
constants::FLOAT_MAT4x3 => {},
|
||||
_ => return Err(InvalidOperation),
|
||||
}
|
||||
let val = self.base.uniform_matrix_section(
|
||||
val,
|
||||
src_offset,
|
||||
src_length,
|
||||
transpose,
|
||||
4 * 3,
|
||||
location,
|
||||
)?;
|
||||
self.base
|
||||
.send_command(WebGLCommand::UniformMatrix4x3fv(location.id(), val));
|
||||
Ok(())
|
||||
});
|
||||
}
|
||||
|
||||
/// https://www.khronos.org/registry/webgl/specs/latest/2.0/#3.7.8
|
||||
fn UniformMatrix2x4fv(
|
||||
&self,
|
||||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
val: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.base.with_location(location, |location| {
|
||||
match location.type_() {
|
||||
constants::FLOAT_MAT2x4 => {},
|
||||
_ => return Err(InvalidOperation),
|
||||
}
|
||||
let val = self.base.uniform_matrix_section(
|
||||
val,
|
||||
src_offset,
|
||||
src_length,
|
||||
transpose,
|
||||
2 * 4,
|
||||
location,
|
||||
)?;
|
||||
self.base
|
||||
.send_command(WebGLCommand::UniformMatrix2x4fv(location.id(), val));
|
||||
Ok(())
|
||||
});
|
||||
}
|
||||
|
||||
/// https://www.khronos.org/registry/webgl/specs/latest/2.0/#3.7.8
|
||||
fn UniformMatrix3x4fv(
|
||||
&self,
|
||||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
val: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.base.with_location(location, |location| {
|
||||
match location.type_() {
|
||||
constants::FLOAT_MAT3x4 => {},
|
||||
_ => return Err(InvalidOperation),
|
||||
}
|
||||
let val = self.base.uniform_matrix_section(
|
||||
val,
|
||||
src_offset,
|
||||
src_length,
|
||||
transpose,
|
||||
3 * 4,
|
||||
location,
|
||||
)?;
|
||||
self.base
|
||||
.send_command(WebGLCommand::UniformMatrix3x4fv(location.id(), val));
|
||||
Ok(())
|
||||
});
|
||||
}
|
||||
|
||||
/// https://www.khronos.org/registry/webgl/specs/latest/2.0/#3.7.8
|
||||
|
@ -1797,6 +1974,42 @@ impl WebGL2RenderingContextMethods for WebGL2RenderingContext {
|
|||
constants::UNSIGNED_INT_VEC4 => unsafe {
|
||||
uniform_typed::<Uint32>(*cx, &uniform_get(triple, WebGLCommand::GetUniformUint4))
|
||||
},
|
||||
constants::FLOAT_MAT2x3 => unsafe {
|
||||
uniform_typed::<Float32>(
|
||||
*cx,
|
||||
&uniform_get(triple, WebGLCommand::GetUniformFloat2x3),
|
||||
)
|
||||
},
|
||||
constants::FLOAT_MAT2x4 => unsafe {
|
||||
uniform_typed::<Float32>(
|
||||
*cx,
|
||||
&uniform_get(triple, WebGLCommand::GetUniformFloat2x4),
|
||||
)
|
||||
},
|
||||
constants::FLOAT_MAT3x2 => unsafe {
|
||||
uniform_typed::<Float32>(
|
||||
*cx,
|
||||
&uniform_get(triple, WebGLCommand::GetUniformFloat3x2),
|
||||
)
|
||||
},
|
||||
constants::FLOAT_MAT3x4 => unsafe {
|
||||
uniform_typed::<Float32>(
|
||||
*cx,
|
||||
&uniform_get(triple, WebGLCommand::GetUniformFloat3x4),
|
||||
)
|
||||
},
|
||||
constants::FLOAT_MAT4x2 => unsafe {
|
||||
uniform_typed::<Float32>(
|
||||
*cx,
|
||||
&uniform_get(triple, WebGLCommand::GetUniformFloat4x2),
|
||||
)
|
||||
},
|
||||
constants::FLOAT_MAT4x3 => unsafe {
|
||||
uniform_typed::<Float32>(
|
||||
*cx,
|
||||
&uniform_get(triple, WebGLCommand::GetUniformFloat4x3),
|
||||
)
|
||||
},
|
||||
_ => self.base.GetUniform(cx, program, location),
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1322,6 +1322,25 @@ impl WebGLRenderingContext {
|
|||
|
||||
Ok(vec)
|
||||
}
|
||||
|
||||
pub fn uniform_matrix_section(
|
||||
&self,
|
||||
vec: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
offset: u32,
|
||||
length: u32,
|
||||
transpose: bool,
|
||||
uniform_size: usize,
|
||||
uniform_location: &WebGLUniformLocation,
|
||||
) -> WebGLResult<Vec<f32>> {
|
||||
let vec = match vec {
|
||||
Float32ArrayOrUnrestrictedFloatSequence::Float32Array(v) => v.to_vec(),
|
||||
Float32ArrayOrUnrestrictedFloatSequence::UnrestrictedFloatSequence(v) => v,
|
||||
};
|
||||
if transpose {
|
||||
return Err(InvalidValue);
|
||||
}
|
||||
self.uniform_vec_section::<f32>(vec, offset, length, uniform_size, uniform_location)
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "webgl_backtrace"))]
|
||||
|
@ -3526,25 +3545,16 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
|
|||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
val: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.with_location(location, |location| {
|
||||
match location.type_() {
|
||||
constants::FLOAT_MAT2 => {},
|
||||
_ => return Err(InvalidOperation),
|
||||
}
|
||||
let val = match val {
|
||||
Float32ArrayOrUnrestrictedFloatSequence::Float32Array(v) => v.to_vec(),
|
||||
Float32ArrayOrUnrestrictedFloatSequence::UnrestrictedFloatSequence(v) => v,
|
||||
};
|
||||
if transpose {
|
||||
return Err(InvalidValue);
|
||||
}
|
||||
if val.len() < 4 || val.len() % 4 != 0 {
|
||||
return Err(InvalidValue);
|
||||
}
|
||||
if location.size().is_none() && val.len() != 4 {
|
||||
return Err(InvalidOperation);
|
||||
}
|
||||
let val =
|
||||
self.uniform_matrix_section(val, src_offset, src_length, transpose, 4, location)?;
|
||||
self.send_command(WebGLCommand::UniformMatrix2fv(location.id(), val));
|
||||
Ok(())
|
||||
});
|
||||
|
@ -3556,25 +3566,16 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
|
|||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
val: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.with_location(location, |location| {
|
||||
match location.type_() {
|
||||
constants::FLOAT_MAT3 => {},
|
||||
_ => return Err(InvalidOperation),
|
||||
}
|
||||
let val = match val {
|
||||
Float32ArrayOrUnrestrictedFloatSequence::Float32Array(v) => v.to_vec(),
|
||||
Float32ArrayOrUnrestrictedFloatSequence::UnrestrictedFloatSequence(v) => v,
|
||||
};
|
||||
if transpose {
|
||||
return Err(InvalidValue);
|
||||
}
|
||||
if val.len() < 9 || val.len() % 9 != 0 {
|
||||
return Err(InvalidValue);
|
||||
}
|
||||
if location.size().is_none() && val.len() != 9 {
|
||||
return Err(InvalidOperation);
|
||||
}
|
||||
let val =
|
||||
self.uniform_matrix_section(val, src_offset, src_length, transpose, 9, location)?;
|
||||
self.send_command(WebGLCommand::UniformMatrix3fv(location.id(), val));
|
||||
Ok(())
|
||||
});
|
||||
|
@ -3586,25 +3587,16 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
|
|||
location: Option<&WebGLUniformLocation>,
|
||||
transpose: bool,
|
||||
val: Float32ArrayOrUnrestrictedFloatSequence,
|
||||
src_offset: u32,
|
||||
src_length: u32,
|
||||
) {
|
||||
self.with_location(location, |location| {
|
||||
match location.type_() {
|
||||
constants::FLOAT_MAT4 => {},
|
||||
_ => return Err(InvalidOperation),
|
||||
}
|
||||
let val = match val {
|
||||
Float32ArrayOrUnrestrictedFloatSequence::Float32Array(v) => v.to_vec(),
|
||||
Float32ArrayOrUnrestrictedFloatSequence::UnrestrictedFloatSequence(v) => v,
|
||||
};
|
||||
if transpose {
|
||||
return Err(InvalidValue);
|
||||
}
|
||||
if val.len() < 16 || val.len() % 16 != 0 {
|
||||
return Err(InvalidValue);
|
||||
}
|
||||
if location.size().is_none() && val.len() != 16 {
|
||||
return Err(InvalidOperation);
|
||||
}
|
||||
let val =
|
||||
self.uniform_matrix_section(val, src_offset, src_length, transpose, 16, location)?;
|
||||
self.send_command(WebGLCommand::UniformMatrix4fv(location.id(), val));
|
||||
Ok(())
|
||||
});
|
||||
|
|
|
@ -439,26 +439,20 @@ interface mixin WebGL2RenderingContextBase
|
|||
void uniform4uiv(WebGLUniformLocation? location, Uint32List data, optional GLuint srcOffset = 0,
|
||||
optional GLuint srcLength = 0);
|
||||
|
||||
// void uniformMatrix2fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
// optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
// void uniformMatrix3x2fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
// optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
// void uniformMatrix4x2fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
// optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
void uniformMatrix3x2fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
void uniformMatrix4x2fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
|
||||
// void uniformMatrix2x3fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
// optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
// void uniformMatrix3fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
// optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
// void uniformMatrix4x3fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
// optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
void uniformMatrix2x3fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
void uniformMatrix4x3fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
|
||||
// void uniformMatrix2x4fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
// optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
// void uniformMatrix3x4fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
// optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
// void uniformMatrix4fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
// optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
void uniformMatrix2x4fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
void uniformMatrix3x4fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
|
||||
/* Vertex attribs */
|
||||
// void vertexAttribI4i(GLuint index, GLint x, GLint y, GLint z, GLint w);
|
||||
|
|
|
@ -668,9 +668,12 @@ interface mixin WebGLRenderingContextBase
|
|||
void uniform4iv(WebGLUniformLocation? location, Int32List data, optional GLuint srcOffset = 0,
|
||||
optional GLuint srcLength = 0);
|
||||
|
||||
void uniformMatrix2fv(WebGLUniformLocation? location, GLboolean transpose, Float32List value);
|
||||
void uniformMatrix3fv(WebGLUniformLocation? location, GLboolean transpose, Float32List value);
|
||||
void uniformMatrix4fv(WebGLUniformLocation? location, GLboolean transpose, Float32List value);
|
||||
void uniformMatrix2fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
void uniformMatrix3fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
void uniformMatrix4fv(WebGLUniformLocation? location, GLboolean transpose, Float32List data,
|
||||
optional GLuint srcOffset = 0, optional GLuint srcLength = 0);
|
||||
|
||||
void useProgram(WebGLProgram? program);
|
||||
void validateProgram(WebGLProgram program);
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue