added instancing, and plenty of little things, fixed lots of bugs
This commit is contained in:
parent
e536a76577
commit
d2df3a998f
@ -4,25 +4,25 @@ cmake_minimum_required(VERSION 2.8)
|
|||||||
find_package(OpenGL REQUIRED)
|
find_package(OpenGL REQUIRED)
|
||||||
|
|
||||||
set(LIB_SRC_LIST
|
set(LIB_SRC_LIST
|
||||||
src/glew.c
|
src/glew.c
|
||||||
src/sparrowrenderer.cpp
|
src/sparrowrenderer.cpp
|
||||||
src/framebuffer.cpp
|
src/framebuffer.cpp
|
||||||
src/meshbuilder.cpp
|
src/meshbuilder.cpp
|
||||||
src/phongmaterial.cpp
|
src/phongmaterial.cpp
|
||||||
src/crappymodule.cpp
|
src/crappymodule.cpp
|
||||||
src/shader.cpp
|
src/shader.cpp
|
||||||
src/skyboxmodule.cpp
|
src/skyboxmodule.cpp
|
||||||
src/parametricmesh.cpp
|
src/parametricmesh.cpp
|
||||||
src/texture.cpp
|
src/texture.cpp
|
||||||
src/scene.cpp
|
src/scene.cpp
|
||||||
src/deferredmodule.cpp
|
src/deferredmodule.cpp
|
||||||
src/forwardmodule.cpp
|
src/forwardmodule.cpp
|
||||||
src/shadersource.cpp
|
src/shadersource.cpp
|
||||||
src/light.cpp
|
src/light.cpp
|
||||||
src/posteffectmodule.cpp
|
src/posteffectmodule.cpp
|
||||||
src/textureblur.cpp
|
src/textureblur.cpp
|
||||||
src/textureredux.cpp
|
src/textureredux.cpp
|
||||||
src/mesh.cpp
|
src/mesh.cpp
|
||||||
)
|
)
|
||||||
|
|
||||||
set(LIBRARY_NAME ${PROJECT_NAME})
|
set(LIBRARY_NAME ${PROJECT_NAME})
|
||||||
@ -35,13 +35,13 @@ set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${LIB_ROOT}) #for SHARED
|
|||||||
set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${LIB_ROOT}) #for STATIC
|
set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${LIB_ROOT}) #for STATIC
|
||||||
|
|
||||||
if(CMAKE_BUILD_TYPE MATCHES "Debug")
|
if(CMAKE_BUILD_TYPE MATCHES "Debug")
|
||||||
set(CPP_DEFINES -DRENDER_DEBUG)
|
set(CPP_DEFINES -DRENDER_DEBUG -DGLEW_BUILD -DGLEW_STATIC)
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
file(GLOB LIBRARY_RES_FILES src/*.h shaders/*.glsl)
|
file(GLOB LIBRARY_RES_FILES src/*.h shaders/*.glsl)
|
||||||
|
|
||||||
add_library(${LIBRARY_NAME} STATIC ${LIB_SRC_LIST} ${LIBRARY_RES_FILES})
|
add_library(${LIBRARY_NAME} STATIC ${LIB_SRC_LIST} ${LIBRARY_RES_FILES})
|
||||||
add_definitions(-std=c++11 ${CPP_DEFINES})
|
add_definitions(-std=c++11 -Wno-comment ${CPP_DEFINES})
|
||||||
|
|
||||||
include_directories(
|
include_directories(
|
||||||
${INCLUDE_ROOT}
|
${INCLUDE_ROOT}
|
||||||
|
@ -3,7 +3,11 @@
|
|||||||
uniform vec3 lightColor;
|
uniform vec3 lightColor;
|
||||||
|
|
||||||
uniform float materialNs;
|
uniform float materialNs;
|
||||||
uniform int objectId;
|
uniform uint objectId;
|
||||||
|
|
||||||
|
#ifdef INSTANCING
|
||||||
|
flat in int instanceId;
|
||||||
|
#endif
|
||||||
|
|
||||||
#ifdef ALPHA_MASK
|
#ifdef ALPHA_MASK
|
||||||
uniform sampler2D alphaMask;
|
uniform sampler2D alphaMask;
|
||||||
@ -53,6 +57,7 @@ uniform float attenuation;
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
layout(location = 0)out vec4 outColor;
|
layout(location = 0)out vec4 outColor;
|
||||||
|
layout(location = 1)out vec4 pickData;
|
||||||
|
|
||||||
vec3 phongLighting(in vec3 kd, in vec3 ks, in float ns, in vec3 color, in vec3 normal, in vec3 lightDir, in vec3 halfVec){
|
vec3 phongLighting(in vec3 kd, in vec3 ks, in float ns, in vec3 color, in vec3 normal, in vec3 lightDir, in vec3 halfVec){
|
||||||
float diffuseComponent = max(dot(normal, lightDir), 0);
|
float diffuseComponent = max(dot(normal, lightDir), 0);
|
||||||
@ -73,7 +78,6 @@ void main(void) {
|
|||||||
|
|
||||||
#ifdef NORMAL_MAP
|
#ifdef NORMAL_MAP
|
||||||
vec3 normal = normalize(texture(normalMap, varTexCoord).xyz * tangentSpace);
|
vec3 normal = normalize(texture(normalMap, varTexCoord).xyz * tangentSpace);
|
||||||
//normal = normalize(vec3(0, 0, 1) * tangentSpace);
|
|
||||||
#else
|
#else
|
||||||
vec3 normal = normalize(varNormal);
|
vec3 normal = normalize(varNormal);
|
||||||
#endif
|
#endif
|
||||||
@ -115,4 +119,14 @@ void main(void) {
|
|||||||
vec3 light = phongLighting(diffuse, specular, materialNs, lightColor, normal, lightDirInView, halfVecInView);
|
vec3 light = phongLighting(diffuse, specular, materialNs, lightColor, normal, lightDirInView, halfVecInView);
|
||||||
outColor = vec4(light*shadow*(1+cos(1.57 + att*1.57)), 1);
|
outColor = vec4(light*shadow*(1+cos(1.57 + att*1.57)), 1);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#ifdef INSTANCING
|
||||||
|
pickData = vec4(gl_FragCoord.z, gl_FragCoord.w, float(int(objectId) + instanceId), 0);
|
||||||
|
#else
|
||||||
|
pickData = vec4(gl_FragCoord.z, gl_FragCoord.w, float(objectId), 0);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef AMBIENT_LIGHT
|
||||||
|
pickData = vec4(0);
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
@ -29,6 +29,12 @@ layout(location = 3)in vec3 inTangent;
|
|||||||
layout(location = 4)in vec3 inBinormal;
|
layout(location = 4)in vec3 inBinormal;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#ifdef INSTANCING
|
||||||
|
layout(location = 5)in vec3 inInstanceOffset;
|
||||||
|
|
||||||
|
flat out int instanceId;
|
||||||
|
#endif
|
||||||
|
|
||||||
#ifndef AMBIENT_LIGHT
|
#ifndef AMBIENT_LIGHT
|
||||||
out vec3 lightDirInView;
|
out vec3 lightDirInView;
|
||||||
out vec3 halfVecInView;
|
out vec3 halfVecInView;
|
||||||
@ -44,7 +50,14 @@ out vec4 posInLightSpace;
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
void main(void) {
|
void main(void) {
|
||||||
vec3 posInView = vec3(modelViewMatrix*vec4(inPosition, 1.0));
|
#ifdef INSTANCING
|
||||||
|
instanceId = gl_InstanceID;
|
||||||
|
vec4 pos = vec4(inPosition + inInstanceOffset, 1.0);
|
||||||
|
#else
|
||||||
|
vec4 pos = vec4(inPosition, 1.0);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
vec3 posInView = vec3(modelViewMatrix*pos);
|
||||||
|
|
||||||
#ifdef DIRECTIONNAL_LIGHT
|
#ifdef DIRECTIONNAL_LIGHT
|
||||||
lightDirInView = normalize(mat3(viewMatrix)*dirLight);
|
lightDirInView = normalize(mat3(viewMatrix)*dirLight);
|
||||||
@ -52,7 +65,7 @@ void main(void) {
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef SHADOWMAP
|
#ifdef SHADOWMAP
|
||||||
posInLightSpace = lightMVP * vec4(inPosition, 1.0);
|
posInLightSpace = lightMVP * pos;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef POINT_LIGHT
|
#ifdef POINT_LIGHT
|
||||||
@ -72,5 +85,5 @@ void main(void) {
|
|||||||
|
|
||||||
varTexCoord = inTexCoord.xy;
|
varTexCoord = inTexCoord.xy;
|
||||||
|
|
||||||
gl_Position = MVP * vec4(inPosition, 1.0);
|
gl_Position = MVP * pos;
|
||||||
}
|
}
|
||||||
|
@ -4,11 +4,12 @@
|
|||||||
#include <glm/mat4x4.hpp>
|
#include <glm/mat4x4.hpp>
|
||||||
|
|
||||||
class Camera{
|
class Camera{
|
||||||
public:
|
public:
|
||||||
virtual glm::mat4 getProjectionMatrix() = 0;
|
virtual glm::mat4 getProjectionMatrix() = 0;
|
||||||
virtual glm::mat4 getViewMatrix() = 0;
|
virtual glm::mat4 getViewMatrix() = 0;
|
||||||
|
|
||||||
virtual void resize(int width, int height) = 0;
|
virtual void resize(int width, int height) = 0;
|
||||||
|
virtual ~Camera(){}//polymorphism
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // CAMERA_H
|
#endif // CAMERA_H
|
||||||
|
@ -11,7 +11,6 @@
|
|||||||
void CrappyModule::renderGL(Camera* myCamera, Scene* scene)
|
void CrappyModule::renderGL(Camera* myCamera, Scene* scene)
|
||||||
{
|
{
|
||||||
glAssert(glEnable(GL_LIGHTING));
|
glAssert(glEnable(GL_LIGHTING));
|
||||||
glAssert(glClearColor(0, 0.1f, 0.05f, 1.0));
|
|
||||||
glAssert(glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT));
|
glAssert(glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT));
|
||||||
glLoadIdentity();
|
glLoadIdentity();
|
||||||
glAssert(glEnable(GL_LIGHT0));
|
glAssert(glEnable(GL_LIGHT0));
|
||||||
@ -28,7 +27,7 @@ void CrappyModule::renderGL(Camera* myCamera, Scene* scene)
|
|||||||
glAssert(glEnable(GL_LIGHT0 + i));
|
glAssert(glEnable(GL_LIGHT0 + i));
|
||||||
glAssert(glLightfv(GL_LIGHT0 + i, GL_AMBIENT, glm::value_ptr(glm::vec4(glm::vec3(0), 1))));
|
glAssert(glLightfv(GL_LIGHT0 + i, GL_AMBIENT, glm::value_ptr(glm::vec4(glm::vec3(0), 1))));
|
||||||
if(l->isDirectionnal()){
|
if(l->isDirectionnal()){
|
||||||
glAssert(glLightfv(GL_LIGHT0 + i, GL_POSITION, glm::value_ptr(glm::vec4(l->getDir(), 0))));
|
glAssert(glLightfv(GL_LIGHT0 + i, GL_POSITION, glm::value_ptr(glm::vec4(-l->getDir(), 0))));
|
||||||
}else{
|
}else{
|
||||||
glAssert(glLightfv(GL_LIGHT0 + i, GL_POSITION, glm::value_ptr(glm::vec4(l->getPos(), 1))));
|
glAssert(glLightfv(GL_LIGHT0 + i, GL_POSITION, glm::value_ptr(glm::vec4(l->getPos(), 1))));
|
||||||
}
|
}
|
||||||
@ -41,12 +40,25 @@ void CrappyModule::renderGL(Camera* myCamera, Scene* scene)
|
|||||||
geometryIt->isValid(); geometryIt->next())
|
geometryIt->isValid(); geometryIt->next())
|
||||||
{
|
{
|
||||||
GeometryNode* node = geometryIt->getItem();
|
GeometryNode* node = geometryIt->getItem();
|
||||||
glMatrixMode(GL_MODELVIEW);
|
|
||||||
glm::mat4 modelViewMatrix = myCamera->getViewMatrix() * node->modelMatrix;
|
|
||||||
glLoadMatrixf(glm::value_ptr(modelViewMatrix));
|
|
||||||
glMatrixMode(GL_PROJECTION);
|
glMatrixMode(GL_PROJECTION);
|
||||||
glLoadMatrixf(glm::value_ptr(myCamera->getProjectionMatrix()));
|
glLoadMatrixf(glm::value_ptr(myCamera->getProjectionMatrix()));
|
||||||
node->mesh->draw();
|
glMatrixMode(GL_MODELVIEW);
|
||||||
|
if(node->mesh->hasInstances())
|
||||||
|
{
|
||||||
|
for(const glm::vec3 &pos : node->mesh->instances_offsets)
|
||||||
|
{
|
||||||
|
glm::mat4 offsetMatrix = glm::translate(node->modelMatrix, pos);
|
||||||
|
glm::mat4 modelViewMatrix = myCamera->getViewMatrix() * offsetMatrix;
|
||||||
|
glLoadMatrixf(glm::value_ptr(modelViewMatrix));
|
||||||
|
node->mesh->draw();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
glm::mat4 modelViewMatrix = myCamera->getViewMatrix() * node->modelMatrix;
|
||||||
|
glLoadMatrixf(glm::value_ptr(modelViewMatrix));
|
||||||
|
node->mesh->draw();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
glAssert(glDisable(GL_LIGHTING));
|
glAssert(glDisable(GL_LIGHTING));
|
||||||
|
@ -8,8 +8,8 @@
|
|||||||
class CrappyModule : public Module
|
class CrappyModule : public Module
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
virtual void renderGL(Camera* myCamera, Scene* scene = NULL);
|
void renderGL(Camera* myCamera, Scene* scene = NULL);
|
||||||
virtual bool requiresModernOpenGL() {return false;}
|
bool requiresModernOpenGL() {return false;}
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // CRAPPYMODULE_H
|
#endif // CRAPPYMODULE_H
|
||||||
|
@ -13,15 +13,19 @@ const char* const ForwardModule::flagStr[] =
|
|||||||
"AMBIENT_TEXTURE",
|
"AMBIENT_TEXTURE",
|
||||||
"SPECULAR_TEXTURE",
|
"SPECULAR_TEXTURE",
|
||||||
"NORMAL_MAP",
|
"NORMAL_MAP",
|
||||||
"ALPHA_MASK"
|
"ALPHA_MASK",
|
||||||
|
"INSTANCING"
|
||||||
};
|
};
|
||||||
|
|
||||||
void ForwardModule::renderGL(Camera* myCamera, Scene* scene)
|
void ForwardModule::renderGL(Camera* myCamera, Scene* scene)
|
||||||
{
|
{
|
||||||
// bind target
|
// bind target
|
||||||
renderTarget->bindFBO();
|
renderTarget->bindFBO();
|
||||||
|
if(clearBeforeDrawing)
|
||||||
|
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||||
|
|
||||||
// render ambient lighting
|
// render ambient lighting
|
||||||
|
glAssert(glEnable(GL_DEPTH_TEST));
|
||||||
glAssert(glDepthFunc(GL_LESS));
|
glAssert(glDepthFunc(GL_LESS));
|
||||||
glAssert(glDisable(GL_BLEND));
|
glAssert(glDisable(GL_BLEND));
|
||||||
|
|
||||||
@ -49,9 +53,9 @@ void ForwardModule::lightPass(Camera* myCamera, Scene* scene, Light* light)
|
|||||||
glAssert(glPolygonMode(GL_FRONT_AND_BACK, GL_FILL));
|
glAssert(glPolygonMode(GL_FRONT_AND_BACK, GL_FILL));
|
||||||
}
|
}
|
||||||
// loop over all types of geometry
|
// loop over all types of geometry
|
||||||
for(int i=0; i<geometryFlagList.size(); ++i)
|
for(std::size_t i=0; i<geometryFlagList.size(); ++i)
|
||||||
{
|
{
|
||||||
int j;
|
std::size_t j;
|
||||||
for(j=0; j<lightFlagList.size(); ++j)
|
for(j=0; j<lightFlagList.size(); ++j)
|
||||||
if(lightFlagList[j] == Light::getFlags(light))
|
if(lightFlagList[j] == Light::getFlags(light))
|
||||||
break;
|
break;
|
||||||
@ -76,7 +80,7 @@ void ForwardModule::lightPass(Camera* myCamera, Scene* scene, Light* light)
|
|||||||
if(light->isShadowCaster())
|
if(light->isShadowCaster())
|
||||||
{
|
{
|
||||||
light->getShadowMap()->bind(NB_FLAGS); // NB_FLAGS has the value of the first available slot after the phong material texture slots
|
light->getShadowMap()->bind(NB_FLAGS); // NB_FLAGS has the value of the first available slot after the phong material texture slots
|
||||||
shader->bindInteger(shader->getLocation("shadowMap"), NB_FLAGS);
|
shader->bindUnsignedInteger(shader->getLocation("shadowMap"), NB_FLAGS);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case Light::POINT:
|
case Light::POINT:
|
||||||
@ -90,12 +94,21 @@ void ForwardModule::lightPass(Camera* myCamera, Scene* scene, Light* light)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
unsigned int id = 2;
|
||||||
for(SceneIterator<GeometryNode*>* geometryIt = scene->getGeometry();
|
for(SceneIterator<GeometryNode*>* geometryIt = scene->getGeometry();
|
||||||
geometryIt->isValid(); geometryIt->next())
|
geometryIt->isValid(); geometryIt->next())
|
||||||
{
|
{
|
||||||
GeometryNode* node = geometryIt->getItem();
|
GeometryNode* node = geometryIt->getItem();
|
||||||
|
shader->bindUnsignedInteger(shader->getLocation("objectId"), id);
|
||||||
|
if(node->mesh->hasInstances())
|
||||||
|
id += node->mesh->instances_offsets.size();
|
||||||
|
else
|
||||||
|
++id;
|
||||||
Material* mat = node->mesh->material;
|
Material* mat = node->mesh->material;
|
||||||
if(mat->getFlags() == geometryFlagList[i]) // if flag matches material
|
unsigned int flags = mat->getFlags();
|
||||||
|
if(node->mesh->hasInstances())
|
||||||
|
flags |= INSTANCING_FLAG;
|
||||||
|
if(flags == geometryFlagList[i]) // if flag matches material
|
||||||
{
|
{
|
||||||
// compute matrix attributes
|
// compute matrix attributes
|
||||||
glm::mat4 modelViewMatrix = myCamera->getViewMatrix() * node->modelMatrix;
|
glm::mat4 modelViewMatrix = myCamera->getViewMatrix() * node->modelMatrix;
|
||||||
@ -143,7 +156,10 @@ void ForwardModule::compileShaders(Scene* scene)
|
|||||||
geometryIt->isValid(); geometryIt->next())
|
geometryIt->isValid(); geometryIt->next())
|
||||||
{
|
{
|
||||||
Mesh* m = geometryIt->getItem()->mesh;
|
Mesh* m = geometryIt->getItem()->mesh;
|
||||||
geometryFlags[m->material->getFlags()] = true;
|
unsigned int flags = m->material->getFlags();
|
||||||
|
if(m->hasInstances())
|
||||||
|
flags |= INSTANCING_FLAG;
|
||||||
|
geometryFlags[flags] = true;
|
||||||
}
|
}
|
||||||
for(int i=0; i<nb_geometry_flags; ++i)
|
for(int i=0; i<nb_geometry_flags; ++i)
|
||||||
{
|
{
|
||||||
@ -188,8 +204,10 @@ void ForwardModule::compileShaders(Scene* scene)
|
|||||||
defines.push_back(flagStr[SPECULAR_TEXTURE]);
|
defines.push_back(flagStr[SPECULAR_TEXTURE]);
|
||||||
if(i & ALPHA_MASK_FLAG)
|
if(i & ALPHA_MASK_FLAG)
|
||||||
defines.push_back(flagStr[ALPHA_MASK]);
|
defines.push_back(flagStr[ALPHA_MASK]);
|
||||||
|
if(i & INSTANCING_FLAG)
|
||||||
|
defines.push_back(flagStr[INSTANCING]);
|
||||||
|
|
||||||
int boundary = defines.size();
|
std::size_t boundary = defines.size();
|
||||||
for(int j : lightFlagList)
|
for(int j : lightFlagList)
|
||||||
{
|
{
|
||||||
while(defines.size() > boundary)
|
while(defines.size() > boundary)
|
||||||
|
@ -19,11 +19,12 @@ public:
|
|||||||
ForwardModule() :
|
ForwardModule() :
|
||||||
shaderSources(NULL),
|
shaderSources(NULL),
|
||||||
renderTarget(FrameBuffer::screen),
|
renderTarget(FrameBuffer::screen),
|
||||||
isWireframe(false)
|
isWireframe(false),
|
||||||
|
clearBeforeDrawing(false)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
virtual void renderGL(Camera* myCamera, Scene* scene);
|
void renderGL(Camera* myCamera, Scene* scene);
|
||||||
virtual bool requiresModernOpenGL() {return true;} // write some compatibility code to change that to false
|
bool requiresModernOpenGL() {return true;} // write some compatibility code to change that to false
|
||||||
|
|
||||||
// modern opengl methods
|
// modern opengl methods
|
||||||
|
|
||||||
@ -32,6 +33,7 @@ public:
|
|||||||
|
|
||||||
void setRenderTarget(const FrameBuffer* target);
|
void setRenderTarget(const FrameBuffer* target);
|
||||||
void setWireframe(bool wireframe) {isWireframe = wireframe;}
|
void setWireframe(bool wireframe) {isWireframe = wireframe;}
|
||||||
|
void setClearBeforeDrawing(bool clear) {clearBeforeDrawing = clear;}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
static const char* const flagStr[NB_FLAGS];
|
static const char* const flagStr[NB_FLAGS];
|
||||||
@ -43,6 +45,7 @@ private:
|
|||||||
const FrameBuffer* renderTarget;
|
const FrameBuffer* renderTarget;
|
||||||
|
|
||||||
bool isWireframe;
|
bool isWireframe;
|
||||||
|
bool clearBeforeDrawing;
|
||||||
|
|
||||||
void lightPass(Camera* myCamera, Scene* scene, Light* light);
|
void lightPass(Camera* myCamera, Scene* scene, Light* light);
|
||||||
};
|
};
|
||||||
|
@ -4,14 +4,15 @@
|
|||||||
|
|
||||||
const FrameBuffer* FrameBuffer::screen = new FrameBuffer(0);
|
const FrameBuffer* FrameBuffer::screen = new FrameBuffer(0);
|
||||||
|
|
||||||
FrameBuffer::FrameBuffer()
|
FrameBuffer::FrameBuffer() :
|
||||||
|
allocated(true)
|
||||||
{
|
{
|
||||||
glAssert(glGenFramebuffers(1, &fbo));
|
glAssert(glGenFramebuffers(1, &fbo));
|
||||||
}
|
}
|
||||||
|
|
||||||
FrameBuffer::~FrameBuffer()
|
FrameBuffer::~FrameBuffer()
|
||||||
{
|
{
|
||||||
if(fbo != 0)
|
if(allocated)
|
||||||
glAssert(glDeleteFramebuffers(1, &fbo));
|
glAssert(glDeleteFramebuffers(1, &fbo));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -29,7 +30,7 @@ void FrameBuffer::addTexture(Texture* tex, GLenum attachment)
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
glAssert(glFramebufferTexture2D(GL_FRAMEBUFFER, attachment, tex->getTarget(), tex->getId(), 0));
|
glAssert(glFramebufferTexture2D(GL_FRAMEBUFFER, attachment, tex->getTarget(), tex->getId(), 0));
|
||||||
if(attachment != GL_DEPTH_ATTACHMENT)
|
if(attachment != GL_DEPTH_ATTACHMENT) // TODO stencil attachment must be tested too
|
||||||
attachments.push_back(attachment);
|
attachments.push_back(attachment);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -52,6 +53,7 @@ void FrameBuffer::deleteTextures()
|
|||||||
{
|
{
|
||||||
for(Texture* t : textures)
|
for(Texture* t : textures)
|
||||||
delete(t);
|
delete(t);
|
||||||
|
textures.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
void FrameBuffer::bindFBO(GLenum target) const
|
void FrameBuffer::bindFBO(GLenum target) const
|
||||||
|
@ -8,17 +8,16 @@ class Texture;
|
|||||||
|
|
||||||
class FrameBuffer
|
class FrameBuffer
|
||||||
{
|
{
|
||||||
private:
|
|
||||||
FrameBuffer(int id) : fbo(id) {}
|
|
||||||
bool check();
|
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
|
bool check();
|
||||||
|
const bool allocated;
|
||||||
GLuint fbo;
|
GLuint fbo;
|
||||||
std::vector<Texture*> textures;
|
std::vector<Texture*> textures;
|
||||||
std::vector<GLuint> attachments;
|
std::vector<GLuint> attachments;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
FrameBuffer();
|
FrameBuffer();
|
||||||
|
FrameBuffer(GLuint id) : allocated(false), fbo(id) {}
|
||||||
~FrameBuffer();
|
~FrameBuffer();
|
||||||
void addTexture(Texture* tex, GLenum attachment);
|
void addTexture(Texture* tex, GLenum attachment);
|
||||||
void initColorAttachments();
|
void initColorAttachments();
|
||||||
|
@ -35,7 +35,7 @@
|
|||||||
#if defined(_WIN32)
|
#if defined(_WIN32)
|
||||||
# include "wglew.h"
|
# include "wglew.h"
|
||||||
#elif !defined(__ANDROID__) && !defined(__native_client__) && !defined(__HAIKU__) && (!defined(__APPLE__) || defined(GLEW_APPLE_GLX))
|
#elif !defined(__ANDROID__) && !defined(__native_client__) && !defined(__HAIKU__) && (!defined(__APPLE__) || defined(GLEW_APPLE_GLX))
|
||||||
# include <GL/glxew.h>
|
# include "glxew.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include <stddef.h> /* For size_t */
|
#include <stddef.h> /* For size_t */
|
||||||
|
1772
src/glxew.h
Normal file
1772
src/glxew.h
Normal file
File diff suppressed because it is too large
Load Diff
@ -6,9 +6,9 @@
|
|||||||
|
|
||||||
struct Image
|
struct Image
|
||||||
{
|
{
|
||||||
int depth;
|
|
||||||
int width;
|
int width;
|
||||||
int height;
|
int height;
|
||||||
|
int depth;
|
||||||
void* pixels;
|
void* pixels;
|
||||||
|
|
||||||
Image() : pixels(NULL) {}
|
Image() : pixels(NULL) {}
|
||||||
|
@ -120,7 +120,7 @@ void Light::generateShadowMap(Scene* scene)
|
|||||||
shaders[1]->bind();
|
shaders[1]->bind();
|
||||||
pmat->alpha_mask->bind(ALPHA_MASK);
|
pmat->alpha_mask->bind(ALPHA_MASK);
|
||||||
shaders[1]->bindMat4(shaders[1]->getLocation("MVP"), lightMVP);
|
shaders[1]->bindMat4(shaders[1]->getLocation("MVP"), lightMVP);
|
||||||
shaders[1]->bindInteger(shaders[1]->getLocation("alphaMask"), ALPHA_MASK);
|
shaders[1]->bindUnsignedInteger(shaders[1]->getLocation("alphaMask"), ALPHA_MASK);
|
||||||
node->mesh->draw(shaders[1], false, true, false);
|
node->mesh->draw(shaders[1], false, true, false);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -53,10 +53,10 @@ public:
|
|||||||
void setColor(glm::vec3 new_color) {color = new_color;}
|
void setColor(glm::vec3 new_color) {color = new_color;}
|
||||||
|
|
||||||
// camera inheritance
|
// camera inheritance
|
||||||
virtual glm::mat4 getProjectionMatrix() {return projectionMatrix;}
|
glm::mat4 getProjectionMatrix() {return projectionMatrix;}
|
||||||
virtual glm::mat4 getViewMatrix() {return viewMatrix;}
|
glm::mat4 getViewMatrix() {return viewMatrix;}
|
||||||
// does nothing, just required for inheriting Camera
|
// does nothing, just required for inheriting Camera
|
||||||
virtual void resize(int width, int height) {}
|
void resize(int width, int height) {}
|
||||||
|
|
||||||
static unsigned int getFlags(Light* l);
|
static unsigned int getFlags(Light* l);
|
||||||
private:
|
private:
|
||||||
|
@ -8,6 +8,7 @@ enum {
|
|||||||
SPECULAR_TEXTURE,
|
SPECULAR_TEXTURE,
|
||||||
NORMAL_MAP,
|
NORMAL_MAP,
|
||||||
ALPHA_MASK,
|
ALPHA_MASK,
|
||||||
|
INSTANCING,
|
||||||
NB_FLAGS
|
NB_FLAGS
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -18,6 +19,7 @@ enum {
|
|||||||
SPECULAR_TEXTURE_FLAG = 1 << SPECULAR_TEXTURE,
|
SPECULAR_TEXTURE_FLAG = 1 << SPECULAR_TEXTURE,
|
||||||
NORMAL_MAP_FLAG = 1 << NORMAL_MAP,
|
NORMAL_MAP_FLAG = 1 << NORMAL_MAP,
|
||||||
ALPHA_MASK_FLAG = 1 << ALPHA_MASK,
|
ALPHA_MASK_FLAG = 1 << ALPHA_MASK,
|
||||||
|
INSTANCING_FLAG = 1 << INSTANCING
|
||||||
};
|
};
|
||||||
|
|
||||||
class Shader;
|
class Shader;
|
||||||
@ -27,6 +29,7 @@ class Material
|
|||||||
public:
|
public:
|
||||||
virtual void bindAttributes(Shader*) = 0;
|
virtual void bindAttributes(Shader*) = 0;
|
||||||
virtual unsigned int getFlags() = 0;
|
virtual unsigned int getFlags() = 0;
|
||||||
|
virtual ~Material(){}
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // MATERIAL_H
|
#endif // MATERIAL_H
|
||||||
|
81
src/mesh.cpp
81
src/mesh.cpp
@ -9,8 +9,10 @@
|
|||||||
|
|
||||||
Mesh::Mesh() :
|
Mesh::Mesh() :
|
||||||
material(NULL),
|
material(NULL),
|
||||||
|
isDoubleSided(false),
|
||||||
vao(0),
|
vao(0),
|
||||||
nb_buffers(0)
|
nb_buffers(0),
|
||||||
|
primitive_type(GL_TRIANGLES)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
Mesh::~Mesh()
|
Mesh::~Mesh()
|
||||||
@ -20,8 +22,7 @@ Mesh::~Mesh()
|
|||||||
|
|
||||||
void Mesh::initGL(bool isDynamic)
|
void Mesh::initGL(bool isDynamic)
|
||||||
{
|
{
|
||||||
if(vao != 0)
|
destroyGL();
|
||||||
destroyGL();
|
|
||||||
|
|
||||||
GLenum buffer_type = isDynamic ? GL_DYNAMIC_DRAW : GL_STATIC_DRAW;
|
GLenum buffer_type = isDynamic ? GL_DYNAMIC_DRAW : GL_STATIC_DRAW;
|
||||||
|
|
||||||
@ -61,12 +62,25 @@ void Mesh::initGL(bool isDynamic)
|
|||||||
glAssert(glBufferData(GL_ARRAY_BUFFER, tangents.size() * sizeof(glm::vec3)*2, tangents.data(), buffer_type));
|
glAssert(glBufferData(GL_ARRAY_BUFFER, tangents.size() * sizeof(glm::vec3)*2, tangents.data(), buffer_type));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(hasInstances() && SparrowRenderer::isModernOpenGLAvailable())
|
||||||
|
{
|
||||||
|
// init instances vbo
|
||||||
|
glAssert(glBindBuffer(GL_ARRAY_BUFFER, vbo[INSTANCE_BUFFER]));
|
||||||
|
glAssert(glBufferData(GL_ARRAY_BUFFER, instances_offsets.size() * sizeof(glm::vec3), instances_offsets.data(), GL_DYNAMIC_DRAW));
|
||||||
|
}
|
||||||
|
|
||||||
// unbind vao
|
// unbind vao
|
||||||
glAssert(glBindVertexArray(0));
|
glAssert(glBindVertexArray(0));
|
||||||
|
glAssert(glBindBuffer(GL_ARRAY_BUFFER, 0));
|
||||||
|
glAssert(glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0));
|
||||||
}
|
}
|
||||||
|
|
||||||
void Mesh::draw(Shader* shader, bool drawNormals, bool drawTexCoord, bool drawTangents)
|
void Mesh::draw(Shader* shader, bool drawNormals, bool drawTexCoord, bool drawTangents)
|
||||||
{
|
{
|
||||||
|
if(isDoubleSided)
|
||||||
|
{
|
||||||
|
glAssert(glDisable(GL_CULL_FACE));
|
||||||
|
}
|
||||||
bool crappy = (shader == NULL);
|
bool crappy = (shader == NULL);
|
||||||
material->bindAttributes(shader);
|
material->bindAttributes(shader);
|
||||||
glAssert(glBindVertexArray(vao));
|
glAssert(glBindVertexArray(vao));
|
||||||
@ -78,8 +92,8 @@ void Mesh::draw(Shader* shader, bool drawNormals, bool drawTexCoord, bool drawTa
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
glAssert(glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(glm::vec3), BUFFER_OFFSET(0)));
|
|
||||||
glAssert(glEnableVertexAttribArray(0));
|
glAssert(glEnableVertexAttribArray(0));
|
||||||
|
glAssert(glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(glm::vec3), BUFFER_OFFSET(0)));
|
||||||
}
|
}
|
||||||
if(hasNormals() && drawNormals)
|
if(hasNormals() && drawNormals)
|
||||||
{
|
{
|
||||||
@ -91,8 +105,8 @@ void Mesh::draw(Shader* shader, bool drawNormals, bool drawTexCoord, bool drawTa
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
glAssert(glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(glm::vec3), BUFFER_OFFSET(0)));
|
|
||||||
glAssert(glEnableVertexAttribArray(1));
|
glAssert(glEnableVertexAttribArray(1));
|
||||||
|
glAssert(glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(glm::vec3), BUFFER_OFFSET(0)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if(hasTexCoords() && drawTexCoord)
|
if(hasTexCoords() && drawTexCoord)
|
||||||
@ -105,22 +119,33 @@ void Mesh::draw(Shader* shader, bool drawNormals, bool drawTexCoord, bool drawTa
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
glAssert(glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, sizeof(glm::vec2), BUFFER_OFFSET(0)));
|
|
||||||
glAssert(glEnableVertexAttribArray(2));
|
glAssert(glEnableVertexAttribArray(2));
|
||||||
|
glAssert(glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, sizeof(glm::vec2), BUFFER_OFFSET(0)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if(hasTangents() && drawTangents && !crappy)
|
if(hasTangents() && drawTangents && !crappy)
|
||||||
{
|
{
|
||||||
glAssert(glBindBuffer(GL_ARRAY_BUFFER, vbo[TANGENT_BUFFER]));
|
glAssert(glBindBuffer(GL_ARRAY_BUFFER, vbo[TANGENT_BUFFER]));
|
||||||
glAssert(glVertexAttribPointer(3, 3, GL_FLOAT, GL_FALSE, sizeof(Mesh::Tangents), BUFFER_OFFSET(0)));
|
|
||||||
glAssert(glEnableVertexAttribArray(3));
|
glAssert(glEnableVertexAttribArray(3));
|
||||||
glAssert(glVertexAttribPointer(4, 3, GL_FLOAT, GL_FALSE, sizeof(Mesh::Tangents), BUFFER_OFFSET(sizeof(glm::vec3))));
|
glAssert(glVertexAttribPointer(3, 3, GL_FLOAT, GL_FALSE, sizeof(Mesh::Tangents), BUFFER_OFFSET(0)));
|
||||||
glAssert(glEnableVertexAttribArray(4));
|
glAssert(glEnableVertexAttribArray(4));
|
||||||
|
glAssert(glVertexAttribPointer(4, 3, GL_FLOAT, GL_FALSE, sizeof(Mesh::Tangents), BUFFER_OFFSET(sizeof(glm::vec3))));
|
||||||
}
|
}
|
||||||
glAssert(glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, vbo[INDICES_BUFFER]));
|
if(!instances_offsets.empty() && !crappy)
|
||||||
glAssert(glDrawElements(GL_TRIANGLES, indices.size(), GL_UNSIGNED_INT, NULL));
|
{
|
||||||
glAssert(glBindVertexArray(0));
|
glAssert(glBindBuffer(GL_ARRAY_BUFFER, vbo[INSTANCE_BUFFER]));
|
||||||
if(crappy)
|
glAssert(glEnableVertexAttribArray(5));
|
||||||
|
glAssert(glVertexAttribPointer(5, 3, GL_FLOAT, GL_FALSE, sizeof(glm::vec3), BUFFER_OFFSET(0)));
|
||||||
|
glAssert(glVertexAttribDivisor(5, 1));
|
||||||
|
glAssert(glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, vbo[INDICES_BUFFER]));
|
||||||
|
glAssert(glDrawElementsInstanced(primitive_type, indices.size(), GL_UNSIGNED_INT, NULL, instances_offsets.size()));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
glAssert(glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, vbo[INDICES_BUFFER]));
|
||||||
|
glAssert(glDrawElements(primitive_type, indices.size(), GL_UNSIGNED_INT, NULL));
|
||||||
|
}
|
||||||
|
if(crappy)
|
||||||
{
|
{
|
||||||
glAssert(glDisableClientState(GL_VERTEX_ARRAY));
|
glAssert(glDisableClientState(GL_VERTEX_ARRAY));
|
||||||
if(hasNormals() && drawNormals)
|
if(hasNormals() && drawNormals)
|
||||||
@ -128,18 +153,35 @@ void Mesh::draw(Shader* shader, bool drawNormals, bool drawTexCoord, bool drawTa
|
|||||||
if(hasTexCoords() && drawTexCoord)
|
if(hasTexCoords() && drawTexCoord)
|
||||||
glAssert(glDisableClientState(GL_TEXTURE_COORD_ARRAY));
|
glAssert(glDisableClientState(GL_TEXTURE_COORD_ARRAY));
|
||||||
}
|
}
|
||||||
|
glAssert(glBindVertexArray(0));
|
||||||
|
if(isDoubleSided)
|
||||||
|
{
|
||||||
|
glAssert(glEnable(GL_CULL_FACE));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Mesh::destroyGL()
|
void Mesh::destroyGL()
|
||||||
{
|
{
|
||||||
if(vbo != NULL)
|
if(vao != 0)
|
||||||
{
|
{
|
||||||
glAssert(glDeleteVertexArrays(1, &vao));
|
|
||||||
glAssert(glDeleteBuffers(NB_BUFFERS, vbo));
|
glAssert(glDeleteBuffers(NB_BUFFERS, vbo));
|
||||||
|
glAssert(glDeleteVertexArrays(1, &vao));
|
||||||
vao = 0;
|
vao = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
glm::vec3* Mesh::beginUpdateBuffer(int buffer)
|
||||||
|
{
|
||||||
|
glAssert(glBindBuffer(GL_ARRAY_BUFFER, vbo[buffer]));
|
||||||
|
glAssert(glm::vec3* ptr = (glm::vec3*)glMapBuffer(GL_ARRAY_BUFFER, GL_WRITE_ONLY));
|
||||||
|
return ptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Mesh::endUpdateBuffer()
|
||||||
|
{
|
||||||
|
glUnmapBuffer(GL_ARRAY_BUFFER);
|
||||||
|
}
|
||||||
|
|
||||||
struct VertexComparator
|
struct VertexComparator
|
||||||
{
|
{
|
||||||
// c'est plutot crade mais j'ai pas trouve d'autre moyen pour le moment
|
// c'est plutot crade mais j'ai pas trouve d'autre moyen pour le moment
|
||||||
@ -183,7 +225,7 @@ void Mesh::mergeVertices()
|
|||||||
std::set<int, VertexComparator> vertexSet;
|
std::set<int, VertexComparator> vertexSet;
|
||||||
VertexComparator::setMesh(this);
|
VertexComparator::setMesh(this);
|
||||||
|
|
||||||
for(int i=0; i<indices.size(); ++i)
|
for(std::size_t i=0; i<indices.size(); ++i)
|
||||||
{
|
{
|
||||||
std::pair<std::set<int,VertexComparator>::iterator,bool> ret = vertexSet.insert(indices[i]);
|
std::pair<std::set<int,VertexComparator>::iterator,bool> ret = vertexSet.insert(indices[i]);
|
||||||
deleted[indices[i]] = !ret.second && *(ret.first) != indices[i];
|
deleted[indices[i]] = !ret.second && *(ret.first) != indices[i];
|
||||||
@ -199,7 +241,7 @@ void Mesh::mergeVertices()
|
|||||||
}
|
}
|
||||||
int offset = 0;
|
int offset = 0;
|
||||||
int pos = 0;
|
int pos = 0;
|
||||||
for(int i=0; i<positions.size(); ++i)
|
for(std::size_t i=0; i<positions.size(); ++i)
|
||||||
{
|
{
|
||||||
if(deleted[i])
|
if(deleted[i])
|
||||||
++offset;
|
++offset;
|
||||||
@ -219,7 +261,7 @@ void Mesh::mergeVertices()
|
|||||||
++pos;
|
++pos;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for(int i=0; i<indices.size(); ++i)
|
for(std::size_t i=0; i<indices.size(); ++i)
|
||||||
indices[i] -= offsets[indices[i]];
|
indices[i] -= offsets[indices[i]];
|
||||||
|
|
||||||
positions.resize(positions.size()-offset);
|
positions.resize(positions.size()-offset);
|
||||||
@ -239,7 +281,8 @@ void Mesh::mergeVertices()
|
|||||||
void Mesh::computeNormals()
|
void Mesh::computeNormals()
|
||||||
{
|
{
|
||||||
normals.resize(positions.size());
|
normals.resize(positions.size());
|
||||||
for (int i=0; i < indices.size(); i += 3)
|
std::memset(normals.data(), 0, normals.size());
|
||||||
|
for (std::size_t i=0; i < indices.size(); i += 3)
|
||||||
{
|
{
|
||||||
int v0 = indices[i];
|
int v0 = indices[i];
|
||||||
int v1 = indices[i+1];
|
int v1 = indices[i+1];
|
||||||
@ -259,7 +302,7 @@ void Mesh::computeTangents()
|
|||||||
return;
|
return;
|
||||||
tangents = std::vector<Tangents>(positions.size());
|
tangents = std::vector<Tangents>(positions.size());
|
||||||
|
|
||||||
for (int j=0; j < indices.size(); j += 3)
|
for (std::size_t j=0; j < indices.size(); j += 3)
|
||||||
{
|
{
|
||||||
int vertexId0 = indices[j];
|
int vertexId0 = indices[j];
|
||||||
int vertexId1 = indices[j+1];
|
int vertexId1 = indices[j+1];
|
||||||
|
37
src/mesh.h
37
src/mesh.h
@ -11,8 +11,6 @@ class Shader;
|
|||||||
|
|
||||||
struct Mesh
|
struct Mesh
|
||||||
{
|
{
|
||||||
protected:
|
|
||||||
|
|
||||||
public: // TODO : see if there is a way to set this protected
|
public: // TODO : see if there is a way to set this protected
|
||||||
// geometry data
|
// geometry data
|
||||||
|
|
||||||
@ -24,16 +22,14 @@ public: // TODO : see if there is a way to set this protected
|
|||||||
|
|
||||||
|
|
||||||
Material* material;
|
Material* material;
|
||||||
|
bool isDoubleSided;
|
||||||
|
|
||||||
std::vector<glm::vec3> positions;
|
std::vector<glm::vec3> positions;
|
||||||
std::vector<glm::vec3> normals;
|
std::vector<glm::vec3> normals;
|
||||||
std::vector<glm::vec2> texCoords;
|
std::vector<glm::vec2> texCoords;
|
||||||
|
std::vector<glm::vec3> instances_offsets;
|
||||||
std::vector<Tangents> tangents;
|
std::vector<Tangents> tangents;
|
||||||
std::vector<unsigned int> indices;
|
std::vector<GLuint> indices;
|
||||||
|
|
||||||
protected:
|
|
||||||
|
|
||||||
// opengl
|
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
// required buffers
|
// required buffers
|
||||||
@ -43,21 +39,39 @@ protected:
|
|||||||
// optionnal buffers :
|
// optionnal buffers :
|
||||||
NORMAL_BUFFER, TEXCOORD_BUFFER, TANGENT_BUFFER,
|
NORMAL_BUFFER, TEXCOORD_BUFFER, TANGENT_BUFFER,
|
||||||
|
|
||||||
|
// instanciation buffer
|
||||||
|
INSTANCE_BUFFER,
|
||||||
|
|
||||||
NB_BUFFERS
|
NB_BUFFERS
|
||||||
};
|
};
|
||||||
|
|
||||||
GLuint vao;
|
GLuint vao; // TODO : this is supposed to be protected
|
||||||
|
|
||||||
|
protected:
|
||||||
|
|
||||||
int nb_buffers;
|
int nb_buffers;
|
||||||
GLuint vbo[NB_BUFFERS];
|
GLuint vbo[NB_BUFFERS];
|
||||||
|
GLenum primitive_type;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
Mesh();
|
Mesh();
|
||||||
~Mesh();
|
virtual ~Mesh();
|
||||||
|
|
||||||
void initGL(bool isDynamic = false);
|
void initGL(bool isDynamic = false);
|
||||||
void draw(Shader* shader = NULL, bool drawNormals = true, bool drawTexCoord = true, bool drawTangents = true);
|
void draw(Shader* shader = NULL, bool drawNormals = true, bool drawTexCoord = true, bool drawTangents = true);
|
||||||
void destroyGL();
|
void destroyGL();
|
||||||
|
|
||||||
|
glm::vec3* beginUpdateBuffer(int buffer);
|
||||||
|
void endUpdateBuffer();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* this class is intended to be used with the default GL_TRIANGLES primitive,
|
||||||
|
* the methods mergeVertices, computeNormals, and computeTangents will probably have
|
||||||
|
* unpredictable behavior with other primitive types.
|
||||||
|
*/
|
||||||
|
void setPrimitiveType(GLenum type) {primitive_type = type;}
|
||||||
|
|
||||||
// merge same vertices
|
// merge same vertices
|
||||||
void mergeVertices();
|
void mergeVertices();
|
||||||
bool operator() (const int& vertId1, const int& vertId2) const;
|
bool operator() (const int& vertId1, const int& vertId2) const;
|
||||||
@ -80,6 +94,11 @@ public:
|
|||||||
{
|
{
|
||||||
return tangents.size() != 0;
|
return tangents.size() != 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool hasInstances() const
|
||||||
|
{
|
||||||
|
return instances_offsets.size() != 0;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // MESH_H
|
#endif // MESH_H
|
||||||
|
@ -10,6 +10,7 @@ public:
|
|||||||
virtual void renderGL(Camera* myCamera, Scene* scene) = 0;
|
virtual void renderGL(Camera* myCamera, Scene* scene) = 0;
|
||||||
virtual bool requiresModernOpenGL() {return true;}
|
virtual bool requiresModernOpenGL() {return true;}
|
||||||
virtual void resize(int width, int height) {}
|
virtual void resize(int width, int height) {}
|
||||||
|
virtual ~Module(){}
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // MODULE
|
#endif // MODULE
|
||||||
|
@ -5,8 +5,11 @@
|
|||||||
#define M_PI 3.14159265358979323846
|
#define M_PI 3.14159265358979323846
|
||||||
#define MAGIC_RATIO 0.37139f
|
#define MAGIC_RATIO 0.37139f
|
||||||
|
|
||||||
Sphere::Sphere(Material* mat, int n)
|
Sphere::Sphere(Material* mat, int n, float myRadius) :
|
||||||
|
radius(myRadius)
|
||||||
{
|
{
|
||||||
|
setMaterial(mat);
|
||||||
|
|
||||||
// icosahedron :
|
// icosahedron :
|
||||||
|
|
||||||
// top cap
|
// top cap
|
||||||
@ -36,6 +39,9 @@ Sphere::Sphere(Material* mat, int n)
|
|||||||
// geodesic subdivisions :
|
// geodesic subdivisions :
|
||||||
for(int i=0; i<n; i++)
|
for(int i=0; i<n; i++)
|
||||||
subdivide();
|
subdivide();
|
||||||
|
|
||||||
|
for(glm::vec3 &vertex : positions)
|
||||||
|
vertex *= radius;
|
||||||
}
|
}
|
||||||
|
|
||||||
int Sphere::getEdge(int a, int b)
|
int Sphere::getEdge(int a, int b)
|
||||||
|
@ -20,11 +20,13 @@ private:
|
|||||||
};
|
};
|
||||||
|
|
||||||
Edge* edges;
|
Edge* edges;
|
||||||
|
float radius;
|
||||||
|
|
||||||
int getEdge(int a, int b);
|
int getEdge(int a, int b);
|
||||||
void createVertex(float u, float v);
|
void createVertex(float u, float v);
|
||||||
void subdivide();
|
void subdivide();
|
||||||
public:
|
public:
|
||||||
Sphere(Material* mat, int n = 0);
|
Sphere(Material* mat, int n = 0, float myRadius = 1.f);
|
||||||
};
|
};
|
||||||
|
|
||||||
class GridMesh : public MeshBuilder
|
class GridMesh : public MeshBuilder
|
||||||
|
@ -15,13 +15,13 @@ void PhongMaterial::bindAttributes(Shader* myShader)
|
|||||||
if(normal_map != NULL)
|
if(normal_map != NULL)
|
||||||
{
|
{
|
||||||
normal_map->bind(NORMAL_MAP);
|
normal_map->bind(NORMAL_MAP);
|
||||||
myShader->bindInteger(myShader->getLocation("normalMap"), NORMAL_MAP);
|
myShader->bindUnsignedInteger(myShader->getLocation("normalMap"), NORMAL_MAP);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(ambient_texture != NULL)
|
if(ambient_texture != NULL)
|
||||||
{
|
{
|
||||||
ambient_texture->bind(AMBIENT_TEXTURE);
|
ambient_texture->bind(AMBIENT_TEXTURE);
|
||||||
myShader->bindInteger(myShader->getLocation("ambientTexture"), AMBIENT_TEXTURE);
|
myShader->bindUnsignedInteger(myShader->getLocation("ambientTexture"), AMBIENT_TEXTURE);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
myShader->bindVec3(myShader->getLocation("materialKa"), ambient);
|
myShader->bindVec3(myShader->getLocation("materialKa"), ambient);
|
||||||
@ -29,7 +29,7 @@ void PhongMaterial::bindAttributes(Shader* myShader)
|
|||||||
if(diffuse_texture != NULL)
|
if(diffuse_texture != NULL)
|
||||||
{
|
{
|
||||||
diffuse_texture->bind(DIFFUSE_TEXTURE);
|
diffuse_texture->bind(DIFFUSE_TEXTURE);
|
||||||
myShader->bindInteger(myShader->getLocation("diffuseTexture"), DIFFUSE_TEXTURE);
|
myShader->bindUnsignedInteger(myShader->getLocation("diffuseTexture"), DIFFUSE_TEXTURE);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
myShader->bindVec3(myShader->getLocation("materialKd"), diffuse);
|
myShader->bindVec3(myShader->getLocation("materialKd"), diffuse);
|
||||||
@ -37,7 +37,7 @@ void PhongMaterial::bindAttributes(Shader* myShader)
|
|||||||
if(specular_texture != NULL)
|
if(specular_texture != NULL)
|
||||||
{
|
{
|
||||||
specular_texture->bind(SPECULAR_TEXTURE);
|
specular_texture->bind(SPECULAR_TEXTURE);
|
||||||
myShader->bindInteger(myShader->getLocation("specularTexture"), SPECULAR_TEXTURE);
|
myShader->bindUnsignedInteger(myShader->getLocation("specularTexture"), SPECULAR_TEXTURE);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
myShader->bindVec3(myShader->getLocation("materialKs"), specular);
|
myShader->bindVec3(myShader->getLocation("materialKs"), specular);
|
||||||
@ -45,7 +45,7 @@ void PhongMaterial::bindAttributes(Shader* myShader)
|
|||||||
if(alpha_mask != NULL)
|
if(alpha_mask != NULL)
|
||||||
{
|
{
|
||||||
alpha_mask->bind(ALPHA_MASK);
|
alpha_mask->bind(ALPHA_MASK);
|
||||||
myShader->bindInteger(myShader->getLocation("alphaMask"), ALPHA_MASK);
|
myShader->bindUnsignedInteger(myShader->getLocation("alphaMask"), ALPHA_MASK);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -33,10 +33,9 @@ public:
|
|||||||
alpha_mask(NULL)
|
alpha_mask(NULL)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
virtual void bindAttributes(Shader* myShader = NULL);
|
void bindAttributes(Shader* myShader = NULL);
|
||||||
|
|
||||||
virtual unsigned int getFlags();
|
unsigned int getFlags();
|
||||||
Shader* getShader() {return shader;}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* deprecated, you should use setDiffuseTexture instead
|
* deprecated, you should use setDiffuseTexture instead
|
||||||
@ -48,9 +47,6 @@ public:
|
|||||||
void setSpecularTexture(Texture* myTexture);
|
void setSpecularTexture(Texture* myTexture);
|
||||||
void setNormalMap(Texture* myNormalMap);
|
void setNormalMap(Texture* myNormalMap);
|
||||||
void setAlphaMask(Texture* myAlphaMask);
|
void setAlphaMask(Texture* myAlphaMask);
|
||||||
|
|
||||||
private:
|
|
||||||
Shader* shader;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // PHONGMATERIAL_H
|
#endif // PHONGMATERIAL_H
|
||||||
|
@ -40,7 +40,7 @@ template <class T>
|
|||||||
class ArraySceneIterator : public SceneIterator<T>
|
class ArraySceneIterator : public SceneIterator<T>
|
||||||
{
|
{
|
||||||
std::vector<T> &vec;
|
std::vector<T> &vec;
|
||||||
int id;
|
unsigned int id;
|
||||||
public:
|
public:
|
||||||
ArraySceneIterator(std::vector<T> &myVec, int myId=0) : vec(myVec), id(myId) {}
|
ArraySceneIterator(std::vector<T> &myVec, int myId=0) : vec(myVec), id(myId) {}
|
||||||
virtual SceneIterator<T>& operator++() {++id; return *this;}
|
virtual SceneIterator<T>& operator++() {++id; return *this;}
|
||||||
@ -61,8 +61,8 @@ public:
|
|||||||
void addLight(Light* myLight) {lights.push_back(myLight);}
|
void addLight(Light* myLight) {lights.push_back(myLight);}
|
||||||
Mesh* getMesh(int id) {return geometry[id]->mesh;}
|
Mesh* getMesh(int id) {return geometry[id]->mesh;}
|
||||||
|
|
||||||
virtual SceneIterator<Light*>* getLights() {return new ArraySceneIterator<Light*>(lights);}
|
SceneIterator<Light*>* getLights() {return new ArraySceneIterator<Light*>(lights);}
|
||||||
virtual SceneIterator<GeometryNode*>* getGeometry() {return new ArraySceneIterator<GeometryNode*>(geometry);}
|
SceneIterator<GeometryNode*>* getGeometry() {return new ArraySceneIterator<GeometryNode*>(geometry);}
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // SCENE_H
|
#endif // SCENE_H
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
#include <glew/glew.h>
|
#include "glew.h"
|
||||||
#include "shader.h"
|
#include "shader.h"
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include "glassert.h"
|
#include "glassert.h"
|
||||||
@ -104,7 +104,7 @@ GLuint Shader::createShader(const std::string &source, GLenum shaderType)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
std::cerr << type_str << " shader not compiled : " << std::endl;
|
std::cerr << type_str << " shader not compiled : " << std::endl;
|
||||||
std::cout << "Shader source :" << std::endl << source << std::endl;
|
//std::cout << "Shader source :" << std::endl << source << std::endl;
|
||||||
printShaderInfoLog(shaderId);
|
printShaderInfoLog(shaderId);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@ -186,7 +186,12 @@ void Shader::bindVec3Array(GLuint location, glm::vec3* vec, int nb_elements)
|
|||||||
glAssert(glUniform3fv(location, nb_elements, (GLfloat*)vec));
|
glAssert(glUniform3fv(location, nb_elements, (GLfloat*)vec));
|
||||||
}
|
}
|
||||||
|
|
||||||
void Shader::bindInteger(GLuint location, GLuint tex_id)
|
void Shader::bindUnsignedInteger(GLuint location, GLuint unsigned_integer)
|
||||||
{
|
{
|
||||||
glAssert(glUniform1i(location, tex_id));
|
glAssert(glUniform1ui(location, unsigned_integer));
|
||||||
|
}
|
||||||
|
|
||||||
|
void Shader::bindInteger(GLuint location, GLint integer)
|
||||||
|
{
|
||||||
|
glAssert(glUniform1i(location, integer));
|
||||||
}
|
}
|
||||||
|
@ -26,7 +26,8 @@ public:
|
|||||||
void bindVec3(GLuint location, glm::vec3 vec);
|
void bindVec3(GLuint location, glm::vec3 vec);
|
||||||
void bindVec4(GLuint location, glm::vec4 vec);
|
void bindVec4(GLuint location, glm::vec4 vec);
|
||||||
void bindVec3Array(GLuint location, glm::vec3* vec, int nb_elements);
|
void bindVec3Array(GLuint location, glm::vec3* vec, int nb_elements);
|
||||||
void bindInteger(GLuint location, GLuint tex_id);
|
void bindUnsignedInteger(GLuint location, GLuint unsigned_integer);
|
||||||
|
void bindInteger(GLuint location, GLint integer);
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // SHADER_H
|
#endif // SHADER_H
|
||||||
|
@ -54,6 +54,14 @@ bool isDefined(const std::string &str, int nbDefines, const char** defines)
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::string ShaderSource::preprocess(std::string source, int nbDefines, const char** defines, const char* version)
|
||||||
|
{
|
||||||
|
std::string header = "#version "+std::string(version);
|
||||||
|
for(int i=0; i<nbDefines; ++i)
|
||||||
|
header += "\n#define"+std::string(defines[i]);
|
||||||
|
return header+"\n#line 1\n"+source;
|
||||||
|
}
|
||||||
|
/*
|
||||||
std::string ShaderSource::preprocess(std::string source, int nbDefines, const char** defines)
|
std::string ShaderSource::preprocess(std::string source, int nbDefines, const char** defines)
|
||||||
{
|
{
|
||||||
std::string compiled = "";
|
std::string compiled = "";
|
||||||
@ -90,3 +98,4 @@ std::string ShaderSource::preprocess(std::string source, int nbDefines, const ch
|
|||||||
}
|
}
|
||||||
return compiled;
|
return compiled;
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
|
@ -26,7 +26,7 @@ public:
|
|||||||
private:
|
private:
|
||||||
std::string* sources[NB_TYPES];
|
std::string* sources[NB_TYPES];
|
||||||
|
|
||||||
std::string preprocess(std::string source, int nbDefines, const char** defines);
|
std::string preprocess(std::string source, int nbDefines, const char** defines, const char* version = "330 core");
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // SHADERSOURCE_H
|
#endif // SHADERSOURCE_H
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
#include <glew/glew.h>
|
#include "glew.h"
|
||||||
#include <GL/gl.h>
|
#include <GL/gl.h>
|
||||||
#include <GL/glext.h>
|
#include <GL/glext.h>
|
||||||
#include <cstdio>
|
#include <cstdio>
|
||||||
@ -8,7 +8,7 @@
|
|||||||
#include "framebuffer.h"
|
#include "framebuffer.h"
|
||||||
#include "module.h"
|
#include "module.h"
|
||||||
#include <chrono>
|
#include <chrono>
|
||||||
|
#include <string.h>
|
||||||
// main methods
|
// main methods
|
||||||
|
|
||||||
bool SparrowRenderer::modernOpenglAvailable = false;
|
bool SparrowRenderer::modernOpenglAvailable = false;
|
||||||
@ -21,12 +21,11 @@ void SparrowRenderer::initGL(int w, int h, bool forceCrappy)
|
|||||||
fprintf(stderr, "Warning: glewInit failed!\n");
|
fprintf(stderr, "Warning: glewInit failed!\n");
|
||||||
if (!forceCrappy &&
|
if (!forceCrappy &&
|
||||||
GLEW_ARB_vertex_program &&
|
GLEW_ARB_vertex_program &&
|
||||||
GLEW_ARB_fragment_program &&
|
|
||||||
GLEW_ARB_texture_float &&
|
|
||||||
GLEW_ARB_draw_buffers &&
|
GLEW_ARB_draw_buffers &&
|
||||||
GLEW_ARB_framebuffer_object &&
|
GLEW_ARB_framebuffer_object &&
|
||||||
glewIsSupported("GL_VERSION_3_3") &&
|
glewIsSupported("GL_VERSION_3_3") &&
|
||||||
GLEW_VERSION_3_3)
|
GLEW_VERSION_3_3 &&
|
||||||
|
strcmp("3.30",(const char *)glGetString(GL_SHADING_LANGUAGE_VERSION))<=0)
|
||||||
{
|
{
|
||||||
modernOpenglAvailable = true;
|
modernOpenglAvailable = true;
|
||||||
printf("Modern OpenGL available.\n");
|
printf("Modern OpenGL available.\n");
|
||||||
@ -68,20 +67,20 @@ void SparrowRenderer::resizeGL(int w, int h)
|
|||||||
|
|
||||||
void SparrowRenderer::renderGL()
|
void SparrowRenderer::renderGL()
|
||||||
{
|
{
|
||||||
FrameBuffer::screen->bindFBO();
|
|
||||||
glAssert(glViewport(0, 0, width, height));
|
glAssert(glViewport(0, 0, width, height));
|
||||||
glAssert(glClearColor(clearColor.r, clearColor.g, clearColor.b, 1));
|
glAssert(glClearColor(clearColor.r, clearColor.g, clearColor.b, 1));
|
||||||
glAssert(glClearDepth(1.0));
|
glAssert(glClearDepth(1.0));
|
||||||
glAssert(glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT));
|
|
||||||
for(ModuleNode &m : modules)
|
for(ModuleNode &m : modules)
|
||||||
{
|
{
|
||||||
if(m.isEnabled)
|
if(m.isEnabled)
|
||||||
{
|
{
|
||||||
|
glFinish();
|
||||||
std::chrono::high_resolution_clock::time_point t = std::chrono::high_resolution_clock::now();
|
std::chrono::high_resolution_clock::time_point t = std::chrono::high_resolution_clock::now();
|
||||||
m.module->renderGL(getCamera(), scene);
|
m.module->renderGL(getCamera(), scene);
|
||||||
m.seconds = std::chrono::duration_cast<std::chrono::duration<double>>(std::chrono::high_resolution_clock::now() - t).count();
|
m.seconds = std::chrono::duration_cast<std::chrono::duration<double>>(std::chrono::high_resolution_clock::now() - t).count();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
glFinish();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool SparrowRenderer::isModernOpenGLAvailable()
|
bool SparrowRenderer::isModernOpenGLAvailable()
|
||||||
@ -134,7 +133,6 @@ void SparrowRenderer::setModuleEnabled(std::string module, bool isEnabled)
|
|||||||
void SparrowRenderer::setCamera(Camera* myCamera)
|
void SparrowRenderer::setCamera(Camera* myCamera)
|
||||||
{
|
{
|
||||||
camera = myCamera;
|
camera = myCamera;
|
||||||
camera->resize(width, height);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Camera* SparrowRenderer::getCamera()
|
Camera* SparrowRenderer::getCamera()
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
#ifndef SPARROWRENDERER_H
|
#ifndef SPARROWRENDERER_H
|
||||||
#define SPARROWRENDERER_H
|
#define SPARROWRENDERER_H
|
||||||
|
|
||||||
|
#include "glew.h"
|
||||||
#include <vector>
|
#include <vector>
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <glm/vec3.hpp>
|
#include <glm/vec3.hpp>
|
||||||
|
Loading…
x
Reference in New Issue
Block a user