Skip to content

Commit

Permalink
test gbuffer
Browse files Browse the repository at this point in the history
  • Loading branch information
colintrinity committed Dec 18, 2017
1 parent 20a7577 commit 7cc2cb6
Show file tree
Hide file tree
Showing 10 changed files with 328 additions and 90 deletions.
20 changes: 9 additions & 11 deletions src/S0.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import { glm } from './glm';
import FlyController from './components/FlyController';
import MouseController from './components/MouseController';
import ForwardRenderer from './renderers/ForwardRenderer';
import DeferredRenderer from './renderers/DeferredRenderer';
import ResoucePipeline from './resources/ResourcePipeline';

import Camera from './Camera';
Expand All @@ -24,11 +25,15 @@ class S0 {
document.getElementById('info').innerHTML = 'WebGL 2 is not available. See <a href="https://www.khronos.org/webgl/wiki/Getting_a_WebGL_Implementation">How to get a WebGL 2 implementation</a>';
return;
}
if (!gl.getExtension("EXT_color_buffer_float")) {
console.error("FLOAT color buffer not available");
document.body.innerHTML = "This example requires EXT_color_buffer_float which is unavailable on this system.";
}

window.gl = gl;
// window.datGUI = new dat.GUI();

this.renderer = new ForwardRenderer(canvas.width, canvas.height);
this.renderer = new DeferredRenderer(canvas.width, canvas.height);
this.onWindowResize();
window.addEventListener('resize', this.onWindowResize.bind(this), false);
canvas.oncontextmenu = function(e) {
Expand Down Expand Up @@ -56,8 +61,8 @@ class S0 {
// 'SimpleTownLite/models/bin_mesh',
// 'SimpleTownLite/models/dumpster_mesh',
// 'SimpleTownLite/models/hotdog_truck_seperate',
// 'SimpleTownLite/models/pizza_car_seperate',
'SimpleTownLite/models/pizza_shop',
'SimpleTownLite/models/pizza_car_seperate',
// 'SimpleTownLite/models/pizza_shop',
// 'SimpleTownLite/models/road_square_mesh',
// 'SimpleTownLite/models/road_straight_clear_mesh',
// 'SimpleTownLite/models/road_straight_mesh',
Expand Down Expand Up @@ -90,14 +95,7 @@ class S0 {
}

render() {
gl.clearColor(0.8, 0.8, 0.8, 1.0);

gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT);
gl.enable(gl.CULL_FACE);

this._scenes.forEach((scene) => {
this.renderer.render(scene, this._camera);
});
this.renderer.render(this._scenes, this._camera);
}

update(dt) {
Expand Down
7 changes: 5 additions & 2 deletions src/core/Shader.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
import vsPBRMaster from '../shaders/unlit.vs.glsl';
import fsPBRMaster from '../shaders/unlit.fs.glsl';
// import vsPBRMaster from '../shaders/unlit.vs.glsl';
// import fsPBRMaster from '../shaders/unlit.fs.glsl';

import vsPBRMaster from '../shaders/deferred/pbr.vs.glsl';
import fsPBRMaster from '../shaders/deferred/pbr.fs.glsl';

export const ShaderManager = {
_shaderCounter: 0,
Expand Down
28 changes: 1 addition & 27 deletions src/primitives/Quad.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,3 @@
import { vec3, vec4, quat, mat4 } from 'gl-matrix';
import vs from '../shaders/quad.vs.glsl';
import fs from '../shaders/quad.fs.glsl';

export default class Quad {
constructor() {
this.vertexData = new Float32Array([
Expand All @@ -10,42 +6,20 @@ export default class Quad {
1.0, 1.0, 0.0, 1.0, 1.0,
1.0, -1.0, 0.0, 1.0, 0.0,
]);

this.program = ShaderStatic.createProgram(gl, vs, fs);
this.uniformMvpLocation = 0;

this.vertexArray = gl.createVertexArray();
this.vertexBuffer = gl.createBuffer();

gl.bindVertexArray(this.vertexArray);
gl.bindBuffer(gl.ARRAY_BUFFER, this.vertexBuffer);
gl.bufferData(gl.ARRAY_BUFFER, this.vertexData, gl.STATIC_DRAW);

gl.vertexAttribPointer(0, 3, gl.FLOAT, false, 5 * 4, 0);
gl.enableVertexAttribArray(0);
gl.vertexAttribPointer(1, 2, gl.FLOAT, false, 5 * 4, 3 * 4);
gl.enableVertexAttribArray(1);

gl.bindVertexArray(null);

gl.useProgram(this.program);
this.uniformMvpLocation = gl.getUniformLocation(this.program, "MVP");
this.texture0Location = gl.getUniformLocation(this.program, "texture_0");
gl.uniform1i(this.texture0Location, 0);
}


draw(V, P) {

let MVP = mat4.create();
gl.useProgram(this.program);
if (this.texture) {
gl.activeTexture(gl.TEXTURE0);
gl.bindTexture(gl.TEXTURE_2D, this.texture);
}
mat4.mul(MVP, V, MVP);
mat4.mul(MVP, P, MVP);
gl.uniformMatrix4fv(this.uniformMvpLocation, false, MVP);
draw() {
gl.bindVertexArray(this.vertexArray);
gl.drawArrays(gl.TRIANGLE_STRIP, 0, 4);
gl.bindVertexArray(null);
Expand Down
234 changes: 200 additions & 34 deletions src/renderers/DeferredRenderer.js
Original file line number Diff line number Diff line change
@@ -1,55 +1,71 @@
import Renderer from './Renderer';
import { /* vec3, vec4, quat,*/ mat4 } from 'gl-matrix';

import Quad from '../primitives/Quad';
import Shader from '../core/Shader';

import vsPBRMaster from '../shaders/deferred/pbr.vs.glsl';
import fsPBRMaster from '../shaders/deferred/pbr.fs.glsl';

import vsComposite from '../shaders/deferred/composite.vs.glsl';
import fsComposite from '../shaders/deferred/composite.fs.glsl';

export default class DeferredRenderer extends Renderer {
constructor(width, height) {
super(width, height);
this._items = [];
// console.log(gl.getParameter(gl.MAX_COLOR_ATTACHMENTS_WEBGL));
// console.log(gl.getParameter(gl.MAX_DRAW_BUFFERS_WEBGL));

this.ext = gl.getExtension('WEBGL_draw_buffers');
if (!this.ext) {
console.log('WEBGL_draw_buffers not supported');
}
this.initializeGBuffer();

this._quad = new Quad();
}

initializeGBuffer() {
let gBuffer = gl.createFramebuffer();
gl.bindFramebuffer(gl.FRAMEBUFFER, gBuffer);
this._gBuffer = gl.createFramebuffer();
gl.bindFramebuffer(gl.FRAMEBUFFER, this._gBuffer);

let gPosition = gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D, gPosition);
this._gPosition = gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D, this._gPosition);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE);
gl.texImage2D(
gl.TEXTURE_2D,
0,
gl.RG16F,
gl.RGBA16F,
this._viewWith,
this._viewHeight,
0,
gl.RGB,
gl.RGBA,
gl.FLOAT,
null
);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST);
gl.framebufferTexture2D(gl.FRAMEBUFFER, this.ext.COLOR_ATTACHMENT0_WEBGL, gl.TEXTURE_2D, gPosition, 0);
gl.framebufferTexture2D(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.TEXTURE_2D, this._gPosition, 0);

let gNormal = gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D, gNormal);
this._gNormal = gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D, this._gNormal);
gl.texImage2D(
gl.TEXTURE_2D,
0,
gl.RG16F,
gl.RGBA16F,
this._viewWith,
this._viewHeight,
0,
gl.RGB,
gl.RGBA,
gl.FLOAT,
null
);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST);
gl.framebufferTexture2D(gl.FRAMEBUFFER, this.ext.COLOR_ATTACHMENT1_WEBGL, gl.TEXTURE_2D, gNormal, 0);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE);
gl.framebufferTexture2D(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT1, gl.TEXTURE_2D, this._gNormal, 0);

let gAlbedoSpec = gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D, gAlbedoSpec);
this._gAlbedoSpec = gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D, this._gAlbedoSpec);
gl.texImage2D(
gl.TEXTURE_2D,
0,
Expand All @@ -61,25 +77,175 @@ export default class DeferredRenderer extends Renderer {
gl.UNSIGNED_BYTE,
null
);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST);
gl.framebufferTexture2D(gl.FRAMEBUFFER, this.ext.COLOR_ATTACHMENT2_WEBGL, gl.TEXTURE_2D, gAlbedoSpec, 0);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE);
gl.framebufferTexture2D(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT2, gl.TEXTURE_2D, this._gAlbedoSpec, 0);

this._gMetallicRoughness = gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D, this._gMetallicRoughness);
gl.texImage2D(
gl.TEXTURE_2D,
0,
gl.RGBA,
this._viewWith,
this._viewHeight,
0,
gl.RGBA,
gl.UNSIGNED_BYTE,
null
);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE);
gl.framebufferTexture2D(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT3, gl.TEXTURE_2D, this._gMetallicRoughness, 0);

this.ext.drawBuffersWEBGL([
this.ext.COLOR_ATTACHMENT0_WEBGL,
this.ext.COLOR_ATTACHMENT1_WEBGL,
this.ext.COLOR_ATTACHMENT2_WEBGL
gl.drawBuffers([
gl.COLOR_ATTACHMENT0,
gl.COLOR_ATTACHMENT1,
gl.COLOR_ATTACHMENT2,
gl.COLOR_ATTACHMENT3
]);

let rboDepth = gl.createRenderbuffer();
gl.bindRenderbuffer(gl.RENDERBUFFER, rboDepth);
gl.renderbufferStorage(gl.RENDERBUFFER, gl.DEPTH_COMPONENT32F, this._viewWith, this._viewHeight);
gl.framebufferRenderbuffer(gl.FRAMEBUFFER, gl.DEPTH_ATTACHMENT, gl.RENDERBUFFER, rboDepth);
let depthRenderBuffer = gl.createRenderbuffer();
gl.bindRenderbuffer(gl.RENDERBUFFER, depthRenderBuffer);
gl.renderbufferStorage(gl.RENDERBUFFER, gl.DEPTH_COMPONENT16, this._viewWith, this._viewHeight);
gl.framebufferRenderbuffer(gl.FRAMEBUFFER, gl.DEPTH_ATTACHMENT, gl.RENDERBUFFER, depthRenderBuffer);

if (gl.checkFramebufferStatus(gl.FRAMEBUFFER) !== gl.FRAMEBUFFER_COMPLETE) {
console.error('Framebuffer not complete!');
}

gl.bindTexture(gl.TEXTURE_2D, null);
gl.bindRenderbuffer(gl.RENDERBUFFER, null);
gl.bindFramebuffer(gl.FRAMEBUFFER, null);

this._shaderCompositePass = new Shader(vsComposite, fsComposite);
this._shaderCompositePass.compile();
}

render(scenes, camera) {
this.renderGeometryPass(scenes, camera);

this.renderComposite();
}

renderGeometryPass(scenes, camera) {
gl.bindFramebuffer(gl.FRAMEBUFFER, this._gBuffer);
gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT);

scenes.forEach((scene) => {
let length = this._items.length;

if (length === 0) {
let root = scene.root;
this._visitNode(root, mat4.create());
}

this.projection = camera.projection;
this.view = camera.view;

length = this._items.length;
for (let i = 0; i < length; i++) {
this._render(this._items[i]);
}

this._items = [];
});

gl.bindFramebuffer(gl.FRAMEBUFFER, null);
}

renderLightingPass() {

}

renderComposite() {

gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT);
this._shaderCompositePass.use();
gl.activeTexture(gl.TEXTURE0);
gl.bindTexture(gl.TEXTURE_2D, this._gPosition);
gl.activeTexture(gl.TEXTURE1);
gl.bindTexture(gl.TEXTURE_2D, this._gNormal);
gl.activeTexture(gl.TEXTURE2);
gl.bindTexture(gl.TEXTURE_2D, this._gAlbedoSpec);
gl.activeTexture(gl.TEXTURE3);
gl.bindTexture(gl.TEXTURE_2D, this._gMetallicRoughness);

this._quad.draw();

// gl.bindFramebuffer(gl.READ_FRAMEBUFFER, this._gBuffer);
// gl.bindFramebuffer(gl.DRAW_FRAMEBUFFER, null);
// gl.blitFramebuffer(0, 0, this._viewWith, this._viewHeight, 0, 0, this._viewWith, this._viewHeight, gl.DEPTH_BUFFER_BIT, gl.NEAREST);
// gl.bindFramebuffer(gl.FRAMEBUFFER, null);
}

//
_visitNode(node, parentMatrix) {

let worldMatrix = mat4.multiply(mat4.create(), parentMatrix, node.localMatrix);

if (node.mesh) {
node.mesh.primitives.forEach((primitive) => {
this._items.push({
primitive: primitive,
worldMatrix: worldMatrix
});
});
}

if (node.children) {
node.children.forEach((child) => {
this._visitNode(child, worldMatrix);
});
}
}

//@TODO
_render(item) {
let MV = mat4.mul(mat4.create(), this.view, item.worldMatrix);
let MVP = mat4.mul(mat4.create(), this.projection, MV);
this.context = {
MVP: MVP,
MV: MV
};
item.primitive.draw(this);
}

//@TODO
useMaterial(material) {
material.shader.use();
material.shader.setMat4("MVP", this.context.MVP);
material.shader.setInt("uBaseColorTexture", 0);
// material.bindTextures();

let texture = material.baseColorTextureInfo.texture;
let index = material.baseColorTextureInfo.index;
let sampler;
if (texture.sampler) {
sampler = texture.sampler.sampler;
} else {
sampler = this.defaultSampler;
}
gl.bindFramebuffer(gl.FRAMEBUFFER, 0);
gl.activeTexture(gl.TEXTURE0 + index);
gl.bindTexture(gl.TEXTURE_2D, texture.texture);
gl.bindSampler(index, sampler);
}

//@TODO
bindVertexArray(id) {
gl.bindVertexArray(id);
}

//@TODO
drawElements(mode, indicesLength, indicesComponentType, indicesOffset) {
gl.drawElements(mode, indicesLength, indicesComponentType, indicesOffset);
}

drawArrays(mode, drawArraysOffset, drawArraysCount) {
gl.drawArrays(mode, drawArraysOffset, drawArraysCount);
}
}
Loading

0 comments on commit 7cc2cb6

Please sign in to comment.