Use glow, GL on Whatever (#262)

Replaces the use of gl_generator with the glow wrapper:

* Add glow dependency, based on glow 0.6.1

* Pin version of glow fork for https://github.com/iceiix/glow/pull/1 until #442 renderbuffer

* Remove gl module, steven_gl

Porting details:
* Initialize glow in src/gl/mod.rs
* Call gl methods on glow context
* glow uses camelcase
* Import glow::HasContext trait, finds draw_elements etc.
* Fix mismatched types, glow uses Option and &str instead of raw pointers
* Fix uniform_location, glow already returns Some(u32)
* uniform_location: convert i32 to u32 for Uniform
* Fix attribute_location
* Fix shader creation Result u32 type 
* Fix passing GLvoid and 2d/3d
* Fix missing Options type mismatches
* Offsets are i32 in glow, not GLvoid
* Fix clear_buffer using _f32_slice
* Delete methods are singular not plural
* glBufferData -> buffer_data_u8_slice
* buffer_sub_data_u8_slice
* Update more glow method wrapper names found by reviewing glow native platform
* Remove unused multi_draw_elements, can be replaced by draw_elements in a loop and it has no WebGL equivalent
* glow implements glMapBufferRange
* Remove unused read_buffer
* glow's deletes automatically pass 1 and take no reference
* shader_source() accepts &str directly; removes last of std::ptr
* Pass uniform Option<u32>
* Fix bool passing normalized parameter
* Fix draw_buffers parameter
* Stop unnecessarily returning context from gl::init
* Getting shader info is unsafe 
* Unwrapping static mut is unsafe
* Use unsafe raw pointers for global mutable context
* Fix initializing GL objects wrappers from glow wrappers
* Unbinding framebuffers uses None
* Uppercase global to fix warning
* Shaders return Some instead of None
* Unbox the context to a raw pointer
* Use tex_image_2d_multisample added in glow fork 
* Implement uniform_location, fixing unwrap None failed
* Add tex_sub_image_3d, using PixelUnpackData::Slice
* set_matrix4: transmute the Matrix4 since it is repr(C)
* get_pixels -> get_tex_image -> glGetTexImage, with PixelPackData::Slice
* Wrap sub_image_2d (glTexSubImage2D) and fix warnings
* Implement set_float_multi_raw and set_matrix4_multi, using from_raw_parts
This commit is contained in:
iceiix 2020-12-25 10:00:22 -08:00 committed by GitHub
parent 9700ffe34d
commit 0aa062f4b8
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
10 changed files with 178 additions and 290 deletions

28
Cargo.lock generated
View File

@ -827,6 +827,17 @@ dependencies = [
"xml-rs",
]
[[package]]
name = "glow"
version = "0.6.1"
source = "git+https://github.com/iceiix/glow?rev=45c808678735e03737d5e1b9d6ed0e21070edcd9#45c808678735e03737d5e1b9d6ed0e21070edcd9"
dependencies = [
"js-sys",
"slotmap",
"wasm-bindgen",
"web-sys",
]
[[package]]
name = "glutin"
version = "0.26.0"
@ -2270,6 +2281,12 @@ version = "0.4.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c111b5bd5695e56cffe5129854aa230b39c93a305372fdbb2668ca2394eea9f8"
[[package]]
name = "slotmap"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c46a3482db8f247956e464d783693ece164ca056e6e67563ee5505bdb86452cd"
[[package]]
name = "smallvec"
version = "0.6.13"
@ -2389,15 +2406,6 @@ dependencies = [
"steven_shared",
]
[[package]]
name = "steven_gl"
version = "0.0.1"
dependencies = [
"gl_generator",
"khronos_api",
"libc",
]
[[package]]
name = "steven_protocol"
version = "0.0.1"
@ -2436,6 +2444,7 @@ dependencies = [
"clipboard",
"collision",
"flate2",
"glow",
"glutin",
"image",
"lazy_static",
@ -2449,7 +2458,6 @@ dependencies = [
"std_or_web",
"stdweb",
"steven_blocks",
"steven_gl",
"steven_protocol",
"steven_resources",
"steven_shared",

View File

@ -21,6 +21,7 @@ opt-level = 1
cfg-if = "1.0.0"
wasm-bindgen = "0.2.69"
glutin = "0.26.0"
glow = { git = "https://github.com/iceiix/glow", rev = "45c808678735e03737d5e1b9d6ed0e21070edcd9" }
byteorder = "1.3.4"
serde = "1.0.118"
serde_json = "1.0.60"
@ -46,10 +47,6 @@ reqwest = { version = "0.10.10", features = [ "blocking" ]}
stdweb = "0.4.20"
winit = { version = "0.24.0", features = [ "stdweb" ]}
[dependencies.steven_gl]
path = "./gl"
version = "0"
[dependencies.steven_resources]
path = "./resources"
version = "0"

56
gl/Cargo.lock generated
View File

@ -1,56 +0,0 @@
# This file is automatically @generated by Cargo.
# It is not intended for manual editing.
[[package]]
name = "cfg-if"
version = "0.1.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "gl_generator"
version = "0.14.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"khronos_api 3.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)",
"xml-rs 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "khronos_api"
version = "3.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "libc"
version = "0.2.66"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "log"
version = "0.4.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"cfg-if 0.1.10 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "steven_gl"
version = "0.0.1"
dependencies = [
"gl_generator 0.14.0 (registry+https://github.com/rust-lang/crates.io-index)",
"khronos_api 3.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "xml-rs"
version = "0.8.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
[metadata]
"checksum cfg-if 0.1.10 (registry+https://github.com/rust-lang/crates.io-index)" = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822"
"checksum gl_generator 0.14.0 (registry+https://github.com/rust-lang/crates.io-index)" = "1a95dfc23a2b4a9a2f5ab41d194f8bfda3cabec42af4e39f08c339eb2a0c124d"
"checksum khronos_api 3.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "e2db585e1d738fc771bf08a151420d3ed193d9d895a36df7f6f8a9456b911ddc"
"checksum libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)" = "d515b1f41455adea1313a4a2ac8a8a477634fbae63cc6100e3aebb207ce61558"
"checksum log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)" = "14b6052be84e6b71ab17edffc2eeabf5c2c3ae1fdb464aae35ac50c67a44e1f7"
"checksum xml-rs 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "541b12c998c5b56aa2b4e6f18f03664eef9a4fd0a246a55594efae6cc2d964b5"

View File

@ -1,13 +0,0 @@
[package]
name = "steven_gl"
version = "0.0.1"
authors = [ "Thinkofdeath <thinkofdeath@spigotmc.org>" ]
edition = "2018"
build = "build.rs"
[build-dependencies]
gl_generator = "0.14.0"
khronos_api = "3.1.0"
[dependencies]
libc = "0.2.71"

View File

@ -1,15 +0,0 @@
use gl_generator::{Api, Fallbacks, GlobalGenerator, Profile, Registry};
use std::env;
use std::fs::File;
use std::io::BufWriter;
use std::path::Path;
fn main() {
let out_dir = env::var("OUT_DIR").unwrap();
let dest = Path::new(&out_dir);
let mut file = BufWriter::new(File::create(&dest.join("bindings.rs")).unwrap());
Registry::new(Api::Gl, (3, 2), Profile::Core, Fallbacks::All, [])
.write_bindings(GlobalGenerator, &mut file)
.unwrap();
}

View File

@ -1,4 +0,0 @@
#![allow(clippy::unused_unit)]
#![allow(clippy::missing_safety_doc)]
#![allow(clippy::too_many_arguments)]
include!(concat!(env!("OUT_DIR"), "/bindings.rs"));

View File

@ -12,18 +12,27 @@
// See the License for the specific language governing permissions and
// limitations under the License.
extern crate steven_gl as gl;
use glow as gl;
use glow::{HasContext, PixelPackData, PixelUnpackData};
use log::{error, info};
use std::ffi;
use std::mem;
use std::ops::BitOr;
use std::ops::{Deref, DerefMut};
use std::ptr;
static mut CONTEXT: *mut glow::Context = 0 as *mut glow::Context;
/// Inits the gl library. This should be called once a context is ready.
pub fn init(vid: &glutin::WindowedContext<glutin::PossiblyCurrent>) {
gl::load_with(|s| vid.get_proc_address(s) as *const _);
unsafe {
let context = Box::new(gl::Context::from_loader_function(|s| {
vid.get_proc_address(s) as *const _
}));
CONTEXT = Box::into_raw(context);
}
}
fn glow_context() -> &'static glow::Context {
unsafe { CONTEXT.as_ref().unwrap() }
}
/// Dsed to specify how the vertices will be handled
@ -42,32 +51,20 @@ pub const POINTS: DrawType = gl::POINTS;
pub fn draw_arrays(ty: DrawType, offset: usize, count: usize) {
unsafe {
gl::DrawArrays(ty, offset as i32, count as i32);
glow_context().draw_arrays(ty, offset as i32, count as i32);
}
}
pub fn draw_elements(ty: DrawType, count: i32, dty: Type, offset: usize) {
unsafe {
gl::DrawElements(ty, count, dty, offset as *const gl::types::GLvoid);
glow_context().draw_elements(ty, count, dty, offset as i32);
}
}
pub fn multi_draw_elements(ty: DrawType, count: &[i32], dty: Type, offsets: &[usize]) {
unsafe {
gl::MultiDrawElements(
ty,
count.as_ptr(),
dty,
offsets.as_ptr() as *const _,
count.len() as i32,
);
}
}
/// Sets the size of the viewport of this context.
// Sets the size of the viewport of this context.
pub fn viewport(x: i32, y: i32, w: i32, h: i32) {
unsafe {
gl::Viewport(x, y, w, h);
glow_context().viewport(x, y, w, h);
}
}
@ -75,7 +72,7 @@ pub fn viewport(x: i32, y: i32, w: i32, h: i32) {
/// when Clear is called with the color flag.
pub fn clear_color(r: f32, g: f32, b: f32, a: f32) {
unsafe {
gl::ClearColor(r, g, b, a);
glow_context().clear_color(r, g, b, a);
}
}
@ -109,12 +106,12 @@ impl BitOr for ClearFlags {
/// Clears the buffers specified by the passed flags.
pub fn clear(flags: ClearFlags) {
unsafe { gl::Clear(flags.internal()) }
unsafe { glow_context().clear(flags.internal()) }
}
pub fn depth_mask(f: bool) {
unsafe {
gl::DepthMask(f as u8);
glow_context().depth_mask(f);
}
}
@ -130,7 +127,7 @@ pub const EQUAL: Func = gl::EQUAL;
pub fn depth_func(f: Func) {
unsafe {
gl::DepthFunc(f);
glow_context().depth_func(f);
}
}
@ -146,14 +143,14 @@ pub const MULTISAMPLE: Flag = gl::MULTISAMPLE;
/// Enables the passed flag.
pub fn enable(f: Flag) {
unsafe {
gl::Enable(f);
glow_context().enable(f);
}
}
/// Disables the passed flag.
pub fn disable(f: Flag) {
unsafe {
gl::Disable(f);
glow_context().disable(f);
}
}
@ -161,7 +158,7 @@ pub fn disable(f: Flag) {
/// currently active one.
pub fn active_texture(id: u32) {
unsafe {
gl::ActiveTexture(gl::TEXTURE0 + id);
glow_context().active_texture(gl::TEXTURE0 + id);
}
}
@ -175,7 +172,7 @@ pub const ZERO_FACTOR: Factor = gl::ZERO;
/// Sets the factors to be used when blending.
pub fn blend_func(s_factor: Factor, d_factor: Factor) {
unsafe {
gl::BlendFunc(s_factor, d_factor);
glow_context().blend_func(s_factor, d_factor);
}
}
@ -186,7 +183,7 @@ pub fn blend_func_separate(
d_factor_a: Factor,
) {
unsafe {
gl::BlendFuncSeparate(s_factor_rgb, d_factor_rgb, s_factor_a, d_factor_a);
glow_context().blend_func_separate(s_factor_rgb, d_factor_rgb, s_factor_a, d_factor_a);
}
}
@ -198,7 +195,7 @@ pub const FRONT: Face = gl::FRONT;
/// Sets the face to be culled by the gpu.
pub fn cull_face(face: Face) {
unsafe {
gl::CullFace(face);
glow_context().cull_face(face);
}
}
@ -211,7 +208,7 @@ pub const COUNTER_CLOCK_WISE: FaceDirection = gl::CCW;
/// Sets the direction of vertices used to specify the
/// front face (e.g. for culling).
pub fn front_face(dir: FaceDirection) {
unsafe { gl::FrontFace(dir) }
unsafe { glow_context().front_face(dir) }
}
/// `Type` is a type of data used by various operations.
@ -270,17 +267,17 @@ pub struct Texture(u32);
impl Texture {
// Allocates a new texture.
pub fn new() -> Texture {
let mut t = Texture(0);
unsafe {
gl::GenTextures(1, &mut t.0);
}
t
Texture(unsafe {
glow_context()
.create_texture()
.expect("create texture failed")
})
}
/// Binds the texture to the passed target.
pub fn bind(&self, target: TextureTarget) {
unsafe {
gl::BindTexture(target, self.0);
glow_context().bind_texture(target, Some(self.0));
}
}
@ -293,13 +290,7 @@ impl Texture {
pixels: &mut [u8],
) {
unsafe {
gl::GetTexImage(
target,
level,
format,
ty,
pixels.as_mut_ptr() as *mut gl::types::GLvoid,
);
glow_context().get_tex_image(target, level, format, ty, PixelPackData::Slice(pixels));
}
}
@ -314,11 +305,7 @@ impl Texture {
pix: Option<&[u8]>,
) {
unsafe {
let ptr = match pix {
Some(val) => val.as_ptr() as *const gl::types::GLvoid,
None => ptr::null(),
};
gl::TexImage2D(
glow_context().tex_image_2d(
target,
level,
format as i32,
@ -327,7 +314,7 @@ impl Texture {
0,
format,
ty,
ptr,
pix,
);
}
}
@ -345,7 +332,7 @@ impl Texture {
pix: &[u8],
) {
unsafe {
gl::TexSubImage2D(
glow_context().tex_sub_image_2d(
target,
level,
x as i32,
@ -354,7 +341,7 @@ impl Texture {
height as i32,
format,
ty,
pix.as_ptr() as *const _,
PixelUnpackData::Slice(pix),
);
}
}
@ -371,11 +358,7 @@ impl Texture {
pix: Option<&[u8]>,
) {
unsafe {
let ptr = match pix {
Some(val) => val.as_ptr() as *const gl::types::GLvoid,
None => ptr::null(),
};
gl::TexImage2D(
glow_context().tex_image_2d(
target,
level,
internal_format as i32,
@ -384,7 +367,7 @@ impl Texture {
0,
format,
ty,
ptr,
pix,
);
}
}
@ -399,25 +382,24 @@ impl Texture {
fixed: bool,
) {
unsafe {
let result: &mut [i32] = &mut [0; 1];
gl::GetIntegerv(gl::MAX_SAMPLES, &mut result[0]);
let use_samples = if samples > result[0] {
let result: i32 = glow_context().get_parameter_i32(gl::MAX_SAMPLES);
let use_samples = if samples > result {
info!(
"glTexImage2DMultisample: requested {} samples but GL_MAX_SAMPLES is {}",
samples, result[0]
samples, result
);
result[0]
result
} else {
samples
};
gl::TexImage2DMultisample(
// TODO: switch to glRenderbufferStorageMultisample https://github.com/iceiix/stevenarella/pull/442
glow_context().tex_image_2d_multisample(
target,
use_samples,
format,
width as i32,
height as i32,
fixed as u8,
fixed,
);
}
}
@ -434,7 +416,7 @@ impl Texture {
pix: &[u8],
) {
unsafe {
gl::TexImage3D(
glow_context().tex_image_3d(
target,
level,
format as i32,
@ -444,7 +426,7 @@ impl Texture {
0,
format,
ty,
pix.as_ptr() as *const gl::types::GLvoid,
Some(pix),
);
}
}
@ -464,7 +446,7 @@ impl Texture {
pix: &[u8],
) {
unsafe {
gl::TexSubImage3D(
glow_context().tex_sub_image_3d(
target,
level,
x as i32,
@ -475,7 +457,7 @@ impl Texture {
depth as i32,
format,
ty,
pix.as_ptr() as *const gl::types::GLvoid,
PixelUnpackData::Slice(pix),
);
}
}
@ -487,7 +469,7 @@ impl Texture {
value: TextureValue,
) {
unsafe {
gl::TexParameteri(target, param, value);
glow_context().tex_parameter_i32(target, param, value);
}
}
}
@ -495,7 +477,7 @@ impl Texture {
impl Drop for Texture {
fn drop(&mut self) {
unsafe {
gl::DeleteTextures(1, &self.0);
glow_context().delete_texture(self.0);
}
}
}
@ -516,31 +498,34 @@ pub struct Program(u32);
impl Program {
pub fn new() -> Program {
Program(unsafe { gl::CreateProgram() })
Program(unsafe {
glow_context()
.create_program()
.expect("program creation failed")
})
}
pub fn attach_shader(&self, shader: Shader) {
unsafe {
gl::AttachShader(self.0, shader.0);
glow_context().attach_shader(self.0, shader.0);
}
}
pub fn link(&self) {
unsafe {
gl::LinkProgram(self.0);
glow_context().link_program(self.0);
}
}
pub fn use_program(&self) {
unsafe {
gl::UseProgram(self.0);
glow_context().use_program(Some(self.0));
}
}
pub fn uniform_location(&self, name: &str) -> Option<Uniform> {
let c_name = ffi::CString::new(name).unwrap();
let u = unsafe { gl::GetUniformLocation(self.0, c_name.as_ptr()) };
if u != -1 {
let u = unsafe { glow_context().get_uniform_location(self.0, name) };
if let Some(u) = u {
Some(Uniform(u))
} else {
None
@ -548,12 +533,9 @@ impl Program {
}
pub fn attribute_location(&self, name: &str) -> Option<Attribute> {
let a = unsafe {
let name_c = ffi::CString::new(name).unwrap();
gl::GetAttribLocation(self.0, name_c.as_ptr())
};
if a != -1 {
Some(Attribute(a))
let a = unsafe { glow_context().get_attrib_location(self.0, name) };
if let Some(a) = a {
Some(Attribute(a as i32))
} else {
None
}
@ -563,7 +545,7 @@ impl Program {
impl Drop for Program {
fn drop(&mut self) {
unsafe {
gl::DeleteProgram(self.0);
glow_context().delete_program(self.0);
}
}
}
@ -572,98 +554,96 @@ pub struct Shader(u32);
impl Shader {
pub fn new(ty: ShaderType) -> Shader {
Shader(unsafe { gl::CreateShader(ty) })
Shader(unsafe {
glow_context()
.create_shader(ty)
.expect("failed to create shader")
})
}
pub fn set_source(&self, src: &str) {
unsafe {
let src_c = ffi::CString::new(src).unwrap();
gl::ShaderSource(self.0, 1, &src_c.as_ptr(), ptr::null());
glow_context().shader_source(self.0, src);
}
}
pub fn compile(&self) {
unsafe {
gl::CompileShader(self.0);
glow_context().compile_shader(self.0);
}
}
pub fn get_parameter(&self, param: ShaderParameter) -> i32 {
let mut ret: i32 = 0;
unsafe {
gl::GetShaderiv(self.0, param, &mut ret);
}
ret
pub fn get_shader_compile_status(&self) -> bool {
unsafe { glow_context().get_shader_compile_status(self.0) }
}
pub fn get_info_log(&self) -> String {
let len = self.get_parameter(INFO_LOG_LENGTH);
let mut data = Vec::<u8>::with_capacity(len as usize);
unsafe {
data.set_len(len as usize);
gl::GetShaderInfoLog(self.0, len, ptr::null_mut(), data.as_mut_ptr() as *mut i8);
}
String::from_utf8(data).unwrap()
unsafe { glow_context().get_shader_info_log(self.0) }
}
}
#[derive(Clone, Copy)]
pub struct Uniform(i32);
pub struct Uniform(u32);
impl Uniform {
pub fn set_int(&self, val: i32) {
unsafe {
gl::Uniform1i(self.0, val);
glow_context().uniform_1_i32(Some(&self.0), val);
}
}
pub fn set_int3(&self, x: i32, y: i32, z: i32) {
unsafe {
gl::Uniform3i(self.0, x, y, z);
glow_context().uniform_3_i32(Some(&self.0), x, y, z);
}
}
pub fn set_float(&self, val: f32) {
unsafe {
gl::Uniform1f(self.0, val);
glow_context().uniform_1_f32(Some(&self.0), val);
}
}
pub fn set_float2(&self, x: f32, y: f32) {
unsafe {
gl::Uniform2f(self.0, x, y);
glow_context().uniform_2_f32(Some(&self.0), x, y);
}
}
pub fn set_float3(&self, x: f32, y: f32, z: f32) {
unsafe {
gl::Uniform3f(self.0, x, y, z);
glow_context().uniform_3_f32(Some(&self.0), x, y, z);
}
}
pub fn set_float4(&self, x: f32, y: f32, z: f32, w: f32) {
unsafe {
gl::Uniform4f(self.0, x, y, z, w);
glow_context().uniform_4_f32(Some(&self.0), x, y, z, w);
}
}
#[allow(clippy::missing_safety_doc)]
pub unsafe fn set_float_multi_raw(&self, data: *const f32, len: usize) {
gl::Uniform4fv(self.0, len as i32, data);
glow_context().uniform_4_f32_slice(Some(&self.0), std::slice::from_raw_parts(data, len));
}
pub fn set_matrix4(&self, m: &::cgmath::Matrix4<f32>) {
use cgmath::Matrix;
unsafe {
gl::UniformMatrix4fv(self.0, 1, false as u8, m.as_ptr());
glow_context().uniform_matrix_4_f32_slice(
Some(&self.0),
false,
&*(m as *const cgmath::Matrix4<f32> as *const [f32; 4 * 4]),
);
}
}
pub fn set_matrix4_multi(&self, m: &[::cgmath::Matrix4<f32>]) {
unsafe {
gl::UniformMatrix4fv(self.0, m.len() as i32, false as u8, m.as_ptr() as *const _);
// TODO: Most likely isn't safe
glow_context().uniform_matrix_4_f32_slice(
Some(&self.0),
false,
std::slice::from_raw_parts(m.as_ptr() as *const _, m.len() * 4 * 4),
); // TODO: Most likely isn't safe
}
}
}
@ -674,38 +654,32 @@ pub struct Attribute(i32);
impl Attribute {
pub fn enable(&self) {
unsafe {
gl::EnableVertexAttribArray(self.0 as u32);
glow_context().enable_vertex_attrib_array(self.0 as u32);
}
}
pub fn disable(&self) {
unsafe {
gl::DisableVertexAttribArray(self.0 as u32);
glow_context().disable_vertex_attrib_array(self.0 as u32);
}
}
pub fn vertex_pointer(&self, size: i32, ty: Type, normalized: bool, stride: i32, offset: i32) {
unsafe {
gl::VertexAttribPointer(
glow_context().vertex_attrib_pointer_f32(
self.0 as u32,
size,
ty,
normalized as u8,
normalized,
stride,
offset as *const gl::types::GLvoid,
offset,
);
}
}
pub fn vertex_pointer_int(&self, size: i32, ty: Type, stride: i32, offset: i32) {
unsafe {
gl::VertexAttribIPointer(
self.0 as u32,
size,
ty,
stride,
offset as *const gl::types::GLvoid,
);
glow_context().vertex_attrib_pointer_i32(self.0 as u32, size, ty, stride, offset);
}
}
}
@ -719,11 +693,11 @@ pub struct VertexArray(u32);
impl VertexArray {
/// Allocates a new `VertexArray`.
pub fn new() -> VertexArray {
let mut va = VertexArray(0);
unsafe {
gl::GenVertexArrays(1, &mut va.0);
}
va
VertexArray(unsafe {
glow_context()
.create_vertex_array()
.expect("create vertex array failed")
})
}
/// Marks the `VertexArray` as the currently active one, this
@ -731,7 +705,7 @@ impl VertexArray {
/// this `VertexArray`.
pub fn bind(&self) {
unsafe {
gl::BindVertexArray(self.0);
glow_context().bind_vertex_array(Some(self.0));
}
}
}
@ -739,7 +713,7 @@ impl VertexArray {
impl Drop for VertexArray {
fn drop(&mut self) {
unsafe {
gl::DeleteVertexArrays(1, &self.0);
glow_context().delete_vertex_array(self.0);
}
self.0 = 0;
}
@ -780,11 +754,11 @@ pub struct Buffer(u32);
impl Buffer {
/// Allocates a new Buffer.
pub fn new() -> Buffer {
let mut b = Buffer(0);
unsafe {
gl::GenBuffers(1, &mut b.0);
}
b
Buffer(unsafe {
glow_context()
.create_buffer()
.expect("create buffer failed")
})
}
/// Makes the buffer the currently active one for the given target.
@ -792,24 +766,19 @@ impl Buffer {
/// (Data, Map etc).
pub fn bind(&self, target: BufferTarget) {
unsafe {
gl::BindBuffer(target, self.0);
glow_context().bind_buffer(target, Some(self.0));
}
}
pub fn set_data(&self, target: BufferTarget, data: &[u8], usage: BufferUsage) {
unsafe {
gl::BufferData(
target,
data.len() as isize,
data.as_ptr() as *const gl::types::GLvoid,
usage,
);
glow_context().buffer_data_u8_slice(target, data, usage);
}
}
pub fn re_set_data(&self, target: BufferTarget, data: &[u8]) {
unsafe {
gl::BufferSubData(target, 0, data.len() as isize, data.as_ptr() as *const _);
glow_context().buffer_sub_data_u8_slice(target, 0, data);
}
}
@ -823,7 +792,11 @@ impl Buffer {
pub fn map(&self, target: BufferTarget, access: Access, length: usize) -> MappedBuffer {
unsafe {
MappedBuffer {
inner: Vec::from_raw_parts(gl::MapBuffer(target, access) as *mut u8, 0, length),
inner: Vec::from_raw_parts(
glow_context().map_buffer_range(target, 0, length as i32, access) as *mut u8,
0,
length,
),
target,
}
}
@ -833,7 +806,7 @@ impl Buffer {
impl Drop for Buffer {
fn drop(&mut self) {
unsafe {
gl::DeleteBuffers(1, &self.0);
glow_context().delete_buffer(self.0);
}
}
}
@ -860,7 +833,7 @@ impl DerefMut for MappedBuffer {
impl Drop for MappedBuffer {
fn drop(&mut self) {
unsafe {
gl::UnmapBuffer(self.target);
glow_context().unmap_buffer(self.target);
}
mem::forget(mem::replace(&mut self.inner, Vec::new()));
}
@ -879,7 +852,7 @@ pub struct Framebuffer(u32);
pub fn check_framebuffer_status() {
unsafe {
let status = gl::CheckFramebufferStatus(gl::FRAMEBUFFER);
let status = glow_context().check_framebuffer_status(gl::FRAMEBUFFER);
let s = match status {
gl::FRAMEBUFFER_UNDEFINED => "GL_FRAMEBUFFER_UNDEFINED",
gl::FRAMEBUFFER_INCOMPLETE_ATTACHMENT => "GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT",
@ -909,7 +882,7 @@ pub fn check_framebuffer_status() {
pub fn check_gl_error() {
unsafe {
loop {
let err = gl::GetError();
let err = glow_context().get_error();
if err == gl::NO_ERROR {
break;
}
@ -921,28 +894,28 @@ pub fn check_gl_error() {
impl Framebuffer {
pub fn new() -> Framebuffer {
let mut fb = Framebuffer(0);
unsafe {
gl::GenFramebuffers(1, &mut fb.0);
}
fb
Framebuffer(unsafe {
glow_context()
.create_framebuffer()
.expect("create framebuffer failed")
})
}
pub fn bind(&self) {
unsafe {
gl::BindFramebuffer(gl::FRAMEBUFFER, self.0);
glow_context().bind_framebuffer(gl::FRAMEBUFFER, Some(self.0));
}
}
pub fn bind_read(&self) {
unsafe {
gl::BindFramebuffer(gl::READ_FRAMEBUFFER, self.0);
glow_context().bind_framebuffer(gl::READ_FRAMEBUFFER, Some(self.0));
}
}
pub fn bind_draw(&self) {
unsafe {
gl::BindFramebuffer(gl::DRAW_FRAMEBUFFER, self.0);
glow_context().bind_framebuffer(gl::DRAW_FRAMEBUFFER, Some(self.0));
}
}
@ -954,7 +927,13 @@ impl Framebuffer {
level: i32,
) {
unsafe {
gl::FramebufferTexture2D(gl::FRAMEBUFFER, attachment, target, tex.0, level);
glow_context().framebuffer_texture_2d(
gl::FRAMEBUFFER,
attachment,
target,
Some(tex.0),
level,
);
}
}
}
@ -962,40 +941,37 @@ impl Framebuffer {
impl Drop for Framebuffer {
fn drop(&mut self) {
unsafe {
gl::DeleteFramebuffers(1, &self.0);
glow_context().delete_framebuffer(self.0);
}
}
}
pub fn unbind_framebuffer() {
unsafe {
gl::BindFramebuffer(gl::FRAMEBUFFER, 0);
glow_context().bind_framebuffer(gl::FRAMEBUFFER, None);
}
}
pub fn unbind_framebuffer_read() {
unsafe {
gl::BindFramebuffer(gl::READ_FRAMEBUFFER, 0);
glow_context().bind_framebuffer(gl::READ_FRAMEBUFFER, None);
}
}
pub fn unbind_framebuffer_draw() {
unsafe {
gl::BindFramebuffer(gl::DRAW_FRAMEBUFFER, 0);
glow_context().bind_framebuffer(gl::DRAW_FRAMEBUFFER, None);
}
}
pub fn draw_buffers(bufs: &[Attachment]) {
unsafe {
gl::DrawBuffers(bufs.len() as i32, bufs.as_ptr());
glow_context().draw_buffers(bufs);
}
}
pub fn bind_frag_data_location(p: &Program, cn: u32, name: &str) {
unsafe {
let name_c = ffi::CString::new(name).unwrap();
gl::BindFragDataLocation(p.0, cn, name_c.as_ptr());
}
unsafe { glow_context().bind_frag_data_location(p.0, cn, name) }
}
pub fn blit_framebuffer(
@ -1011,7 +987,7 @@ pub fn blit_framebuffer(
filter: TextureValue,
) {
unsafe {
gl::BlitFramebuffer(
glow_context().blit_framebuffer(
sx0,
sy0,
sx1,
@ -1026,17 +1002,12 @@ pub fn blit_framebuffer(
}
}
pub fn read_buffer(a: Attachment) {
unsafe {
gl::ReadBuffer(a);
}
}
pub type TargetBuffer = u32;
pub const COLOR: TargetBuffer = gl::COLOR;
pub fn clear_buffer(buffer: TargetBuffer, draw_buffer: i32, values: &[f32]) {
pub fn clear_buffer(buffer: TargetBuffer, draw_buffer: u32, values: &mut [f32]) {
unsafe {
gl::ClearBufferfv(buffer, draw_buffer, values.as_ptr());
// TODO: why does glow have &mut on clear buffer values, why would it change the color?
glow_context().clear_buffer_f32_slice(buffer, draw_buffer, values);
}
}

View File

@ -46,7 +46,7 @@ impl Clouds {
v.set_source(&vertex);
v.compile();
if v.get_parameter(gl::COMPILE_STATUS) == 0 {
if !v.get_shader_compile_status() {
error!("Src: {}", vertex);
panic!("Shader error: {}", v.get_info_log());
} else {
@ -61,7 +61,7 @@ impl Clouds {
g.set_source(&geo);
g.compile();
if g.get_parameter(gl::COMPILE_STATUS) == 0 {
if !g.get_shader_compile_status() {
error!("Src: {}", geo);
panic!("Shader error: {}", g.get_info_log());
} else {
@ -76,7 +76,7 @@ impl Clouds {
f.set_source(&fragment);
f.compile();
if f.get_parameter(gl::COMPILE_STATUS) == 0 {
if !f.get_shader_compile_status() {
error!("Src: {}", fragment);
panic!("Shader error: {}", f.get_info_log());
} else {

View File

@ -412,8 +412,8 @@ impl Renderer {
trans.trans.bind();
gl::clear_color(0.0, 0.0, 0.0, 1.0);
gl::clear(gl::ClearFlags::Color);
gl::clear_buffer(gl::COLOR, 0, &[0.0, 0.0, 0.0, 1.0]);
gl::clear_buffer(gl::COLOR, 1, &[0.0, 0.0, 0.0, 0.0]);
gl::clear_buffer(gl::COLOR, 0, &mut [0.0, 0.0, 0.0, 1.0]);
gl::clear_buffer(gl::COLOR, 1, &mut [0.0, 0.0, 0.0, 0.0]);
gl::blend_func_separate(
gl::ONE_FACTOR,
gl::ONE_FACTOR,

View File

@ -131,7 +131,7 @@ pub fn create_program(vertex: &str, fragment: &str) -> gl::Program {
v.set_source(vertex);
v.compile();
if v.get_parameter(gl::COMPILE_STATUS) == 0 {
if !v.get_shader_compile_status() {
error!("Src: {}", vertex);
panic!("Shader error: {}", v.get_info_log());
} else {
@ -146,7 +146,7 @@ pub fn create_program(vertex: &str, fragment: &str) -> gl::Program {
f.set_source(fragment);
f.compile();
if f.get_parameter(gl::COMPILE_STATUS) == 0 {
if !f.get_shader_compile_status() {
error!("Src: {}", fragment);
panic!("Shader error: {}", f.get_info_log());
} else {