Browse Source

nice shader effects (blurlike shit), codebase for video 5

master
Joshua Moerman 14 years ago
parent
commit
523d8de33f
  1. 99
      App.h
  2. 7
      GlutTest.cbp
  3. 113
      fbo.h
  4. 7
      globals.h
  5. 7
      main.cpp
  6. 2
      pngwriter/pngwriter.h
  7. 12
      resources/myHBlurShader.frag
  8. 5
      resources/myHBlurShader.vert
  9. 2
      resources/myTeaShader.frag
  10. 3
      resources/myTeaShader.vert
  11. 8
      resources/myTextureShader.frag
  12. 5
      resources/myTextureShader.vert
  13. 12
      resources/myVBlurShader.frag
  14. 5
      resources/myVBlurShader.vert
  15. 9
      shader.h

99
App.h

@ -21,15 +21,31 @@ static const std::string filenames[] = {
"resources/attractor_2011-04-29_04-34-41-9.stf", "resources/attractor_2011-04-29_04-34-41-9.stf",
"resources/attractor_2011-04-29_15-19-03-9.stf" }; "resources/attractor_2011-04-29_15-19-03-9.stf" };
static const GLfloat quad[] = {
1.0, 1.0,
1.0, -1.0,
-1.0, -1.0,
-1.0, 1.0 };
static const GLfloat tex_quad[] = {
1.0, 1.0,
1.0, 0.0,
0.0, 0.0,
0.0, 1.0 };
class App { class App {
int counter; int counter;
unsigned int width, height; unsigned int width, height;
shader mshader; shader mshader;
shader clear_shader; shader clear_shader;
fbo mfbo; shader texture_shader;
shader blur_shader1;
shader blur_shader2;
fbo fbo1;
fbo fbo2;
static constexpr size_t number_of_lines = 6*50000; static constexpr size_t number_of_lines = 40000;
static constexpr size_t number_of_vertices = 2*number_of_lines; static constexpr size_t number_of_vertices = 2*number_of_lines;
std::array<GLfloat, 3*number_of_vertices> lines; std::array<GLfloat, 3*number_of_vertices> lines;
std::array<GLfloat, 7> parameters; std::array<GLfloat, 7> parameters;
@ -42,12 +58,19 @@ public:
height(h), height(h),
mshader("resources/myTeaShader.vert", "resources/myTeaShader.frag"), mshader("resources/myTeaShader.vert", "resources/myTeaShader.frag"),
clear_shader("resources/myClearShader.vert", "resources/myClearShader.frag"), clear_shader("resources/myClearShader.vert", "resources/myClearShader.frag"),
mfbo(width, height) { texture_shader("resources/myTextureShader.vert", "resources/myTextureShader.frag"),
blur_shader1("resources/myHBlurShader.vert", "resources/myHBlurShader.frag"),
blur_shader2("resources/myVBlurShader.vert", "resources/myVBlurShader.frag"),
fbo1(width, height),
fbo2(width, height),
lines(),
parameters(),
random_parameters() {
set_points(); set_points();
//glEnable(GL_DEPTH_TEST); //glEnable(GL_DEPTH_TEST);
glEnable(GL_BLEND); glEnable(GL_BLEND);
glPointSize(1.0); glEnable(GL_TEXTURE_2D);
std::string filename = filenames[3]; std::string filename = filenames[3];
set_parameters(filename); set_parameters(filename);
@ -57,63 +80,79 @@ public:
} }
void resize(int w, int h) { void resize(int w, int h) {
std::cout << w << "x" << h << std::endl;
} }
void update() { void update() {
++counter; ++counter;
iterate(); iterate();
if(counter % 500 == 0) { if(counter % 5000 == 0) {
set_parameters(filenames[rand() % 4]); set_parameters(filenames[rand() % 4]);
set_points(); set_points();
} }
} }
void draw() { void draw() {
clear_shader.begin(); fbo & read_fbo = (counter % 2) ? fbo1 : fbo2;
clear_shader.set_uniform("fade", .5f); fbo & draw_fbo = (counter % 2) ? fbo2 : fbo1;
if( counter < 5 ) shader & blur_shader = (counter % 2) ? blur_shader1 : blur_shader2;
clear_shader.set_uniform("fade", 1.0f);
fade(); glClearColor(0.0, 0.0, 0.0, 0.0);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
draw_fbo.begin();
glClearColor(0.0, 0.0, 0.0, 0.0);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
blur_shader.begin();
texture(read_fbo);
mshader.begin(); mshader.begin();
mshader.set_uniform("steps", counter); scene();
draw_fbo.end();
glRotatef(0.5, std::sin(counter/1337.0), 1.0, 0.0); texture_shader.begin();
texture(draw_fbo);
scene(); //save_screen();
} }
void fade() { void fade() {
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
static const GLfloat quad[] = {
1.0, 1.0,
1.0, -1.0,
-1.0, -1.0,
-1.0, 1.0 };
glEnableClientState(GL_VERTEX_ARRAY); glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(2, GL_FLOAT, 0, &quad[0]); glVertexPointer(2, GL_FLOAT, 0, &quad[0]);
// draw a cube
glDrawArrays(GL_QUADS, 0, 4); glDrawArrays(GL_QUADS, 0, 4);
glDisableClientState(GL_VERTEX_ARRAY);
}
// deactivate vertex arrays after drawing void texture(fbo const & read_fbo) {
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
texture_shader.set_texture("tex", GL_TEXTURE_2D, read_fbo.texture_id, 0);
glEnableClientState(GL_VERTEX_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glVertexPointer(2, GL_FLOAT, 0, &quad[0]);
glTexCoordPointer(2, GL_FLOAT, 0, &tex_quad[0]);
glDrawArrays(GL_QUADS, 0, 4);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);
glDisableClientState(GL_VERTEX_ARRAY); glDisableClientState(GL_VERTEX_ARRAY);
} }
void scene() { void scene() {
glBlendFunc(GL_ONE, GL_ONE); glBlendFunc(GL_ONE, GL_ONE);
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(3, GL_FLOAT, 0, &lines[0]);
// draw a cube mshader.set_uniform("steps", counter/10);
glDrawArrays(GL_POINTS, 0, number_of_vertices); glRotatef(0.05, std::sin(counter/13370.0), 1.0, 0.0);
// deactivate vertex arrays after drawing const unsigned int part = 8;
glDisableClientState(GL_VERTEX_ARRAY);
//save_screen(); glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(3, GL_FLOAT, 0, &lines[0]);
glPointSize(3.0);
glDrawArrays(GL_POINTS, 0, number_of_vertices/part);
glPointSize(1.0);
glDrawArrays(GL_POINTS, number_of_vertices/part, (part-1)*number_of_vertices/part);
glDisableClientState(GL_VERTEX_ARRAY);
} }
void iterate() { void iterate() {
@ -159,7 +198,7 @@ public:
for(unsigned int i = 0; i < 7; ++i) { for(unsigned int i = 0; i < 7; ++i) {
stfu::node const attractorParameters = file.getChild("AttractorKernel").getChild("parameters"); stfu::node const attractorParameters = file.getChild("AttractorKernel").getChild("parameters");
parameters[i] = atof(attractorParameters.getValue(i).c_str()); parameters[i] = atof(attractorParameters.getValue(i).c_str());
random_parameters[i] = (rand() / (double)RAND_MAX - 0.5) * counter / 500000.0; random_parameters[i] = (rand() / (double)RAND_MAX - 0.5) * counter / 5000000.0;
} }
} }

7
GlutTest.cbp

@ -40,13 +40,20 @@
</Linker> </Linker>
<Unit filename="App.h" /> <Unit filename="App.h" />
<Unit filename="fbo.h" /> <Unit filename="fbo.h" />
<Unit filename="globals.h" />
<Unit filename="main.cpp" /> <Unit filename="main.cpp" />
<Unit filename="pngwriter/pngwriter.cc" /> <Unit filename="pngwriter/pngwriter.cc" />
<Unit filename="pngwriter/pngwriter.h" /> <Unit filename="pngwriter/pngwriter.h" />
<Unit filename="resources/myClearShader.frag" /> <Unit filename="resources/myClearShader.frag" />
<Unit filename="resources/myClearShader.vert" /> <Unit filename="resources/myClearShader.vert" />
<Unit filename="resources/myHBlurShader.frag" />
<Unit filename="resources/myHBlurShader.vert" />
<Unit filename="resources/myTeaShader.frag" /> <Unit filename="resources/myTeaShader.frag" />
<Unit filename="resources/myTeaShader.vert" /> <Unit filename="resources/myTeaShader.vert" />
<Unit filename="resources/myTextureShader.frag" />
<Unit filename="resources/myTextureShader.vert" />
<Unit filename="resources/myVBlurShader.frag" />
<Unit filename="resources/myVBlurShader.vert" />
<Unit filename="shader.h" /> <Unit filename="shader.h" />
<Unit filename="stfu/stf.cpp" /> <Unit filename="stfu/stf.cpp" />
<Unit filename="stfu/stf.hpp" /> <Unit filename="stfu/stf.hpp" />

113
fbo.h

@ -6,18 +6,17 @@
#include <GL/glew.h> #include <GL/glew.h>
#include <GL/freeglut.h> #include <GL/freeglut.h>
class fbo { class fbo {
public:
int width, height; int width, height;
GLuint fbo_number; GLuint fbo_number;
std::map<GLenum, GLuint> renderbuffers; std::map<GLenum, GLuint> renderbuffers;
GLuint texture_id; GLuint texture_id;
public: public:
fbo(int width, int height) : width(width), height(height) { fbo(int width, int height) : width(width), height(height), fbo_number(0), renderbuffers(), texture_id(0) {
check_status(); glGenFramebuffers(1, &fbo_number);
glGenBuffers(1, &fbo_number); bind();
begin();
// generate texture // generate texture
glGenTextures(1, &texture_id); glGenTextures(1, &texture_id);
@ -30,9 +29,14 @@ public:
create_attach_renderbuffer(GL_DEPTH_COMPONENT, GL_DEPTH_ATTACHMENT); create_attach_renderbuffer(GL_DEPTH_COMPONENT, GL_DEPTH_ATTACHMENT);
// attach stencil // attach stencil
create_attach_renderbuffer(GL_STENCIL_INDEX, GL_STENCIL_ATTACHMENT); //create_attach_renderbuffer(GL_STENCIL_INDEX, GL_STENCIL_ATTACHMENT);
check_status(); check_status();
glClearColor(0.0, 0.0, 0.0, 0.0);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
unbind();
} }
~fbo() { ~fbo() {
end(); end();
@ -47,14 +51,33 @@ public:
} }
void begin(){ void begin(){
glBindFramebuffer(GL_FRAMEBUFFER, fbo_number); bind();
//glPushAttrib(GL_VIEWPORT);
//glViewport(0, 0, width, height);
/*GLint savedFramebuffer = -1;
glGetIntegerv(GL_FRAMEBUFFER_BINDING, &savedFramebuffer);
std::cout << "sfb: " << savedFramebuffer << ", fbo: " << fbo_number << std::endl;*/
} }
void end(){ void end(){
glBindFramebuffer(GL_FRAMEBUFFER, 0); unbind();
//glPopAttrib();
} }
private: private:
void bind(){
glBindFramebuffer(GL_FRAMEBUFFER, fbo_number);
GLenum status = glGetError();
if(status != GL_NO_ERROR)
throw std::runtime_error("i has error" + std::to_string(status) + "with fbo: " + std::to_string(fbo_number));
}
void unbind(){
glBindFramebuffer(GL_FRAMEBUFFER, 0);
}
void create_attach_renderbuffer(GLenum format, GLenum attachment_point) { void create_attach_renderbuffer(GLenum format, GLenum attachment_point) {
GLuint buffer; GLuint buffer;
glGenRenderbuffers(1, &buffer); glGenRenderbuffers(1, &buffer);
@ -66,42 +89,46 @@ private:
} }
void check_status() { void check_status() {
GLenum status = glCheckFramebufferStatus(GL_FRAMEBUFFER);
switch(status) {
case GL_FRAMEBUFFER_COMPLETE:
std::cout << "FRAMEBUFFER_COMPLETE - OK" << std::endl;
return;
case GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT:
std::cout << "FRAMEBUFFER_INCOMPLETE_ATTACHMENT" << std::endl;
break;
case GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT:
std::cout << "FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT" << std::endl;
break;
/*case GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS:
std::cout << "FRAMEBUFFER_INCOMPLETE_DIMENSIONS" << std::endl;
break;
case GL_FRAMEBUFFER_INCOMPLETE_FORMATS:
std::cout << "FRAMEBUFFER_INCOMPLETE_FORMATS" << std::endl;
break;*/
case GL_FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER:
std::cout << "FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER" << std::endl;
break;
case GL_FRAMEBUFFER_INCOMPLETE_READ_BUFFER:
std::cout << "FRAMEBUFFER_INCOMPLETE_READ_BUFFER" << std::endl;
break;
case GL_FRAMEBUFFER_UNSUPPORTED:
std::cout << "FRAMEBUFFER_UNSUPPORTED" << std::endl;
break;
case GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE:
std::cout << "GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE" << std::endl;
break;
default:
std::cout << "UNKNOWN FRAMEBUFFER ERROR" << std::endl;
break;
}
//throw std::runtime_error("I will not continu..");
}
void check_error(){
GLenum status = glGetError(); GLenum status = glGetError();
if(status != GL_NO_ERROR) { if(status != GL_NO_ERROR){
status = glCheckFramebufferStatus(GL_FRAMEBUFFER); throw std::runtime_error("GL Error: " + std::to_string(status));
switch(status) {
case GL_FRAMEBUFFER_COMPLETE:
std::cout << "FRAMEBUFFER_COMPLETE - OK" << std::endl;
return;
case GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT:
std::cout << "FRAMEBUFFER_INCOMPLETE_ATTACHMENT" << std::endl;
break;
case GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT:
std::cout << "FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT" << std::endl;
break;
/*case GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS:
std::cout << "FRAMEBUFFER_INCOMPLETE_DIMENSIONS" << std::endl;
break;
case GL_FRAMEBUFFER_INCOMPLETE_FORMATS:
std::cout << "FRAMEBUFFER_INCOMPLETE_FORMATS" << std::endl;
break;*/
case GL_FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER:
std::cout << "FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER" << std::endl;
break;
case GL_FRAMEBUFFER_INCOMPLETE_READ_BUFFER:
std::cout << "FRAMEBUFFER_INCOMPLETE_READ_BUFFER" << std::endl;
break;
case GL_FRAMEBUFFER_UNSUPPORTED:
std::cout << "FRAMEBUFFER_UNSUPPORTED" << std::endl;
break;
case GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE:
std::cout << "GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE" << std::endl;
break;
default:
std::cout << "UNKNOWN FRAMEBUFFER ERROR" << std::endl;
break;
}
throw std::runtime_error("I will not continu..");
} }
} }

7
globals.h

@ -0,0 +1,7 @@
#ifndef globals_h
#define globals_h
#define kWindowWidth 800
#define kWindowHeight 600
#endif // globals_h

7
main.cpp

@ -7,13 +7,11 @@
#include <GL/freeglut.h> #include <GL/freeglut.h>
#include "App.h" #include "App.h"
#include "globals.h"
#define kWindowWidth 1280
#define kWindowHeight 700
App* app_ptr = 0; App* app_ptr = 0;
unsigned int const frames_per_second = 100.0; unsigned int const frames_per_second = 60.0;
typedef std::chrono::high_resolution_clock clock_type; typedef std::chrono::high_resolution_clock clock_type;
@ -64,6 +62,7 @@ int main(int argc, char** argv) {
//glFlush(); //glFlush();
++frame_count; ++frame_count;
if(frame_count == 7400) exit(0);
previous_timepoint = current_timepoint-(difference%time_step); previous_timepoint = current_timepoint-(difference%time_step);
} else { } else {

2
pngwriter/pngwriter.h

@ -88,7 +88,7 @@ using namespace std;
#define PNG_BYTES_TO_CHECK (4) #define PNG_BYTES_TO_CHECK (4)
#define PNGWRITER_DEFAULT_COMPRESSION (6) #define PNGWRITER_DEFAULT_COMPRESSION (0)
class pngwriter { class pngwriter {
private: private:

12
resources/myHBlurShader.frag

@ -0,0 +1,12 @@
uniform sampler2D tex;
vec2 offset = vec2(0.0, 1.0/600.0);
void main( void ) {
gl_FragColor = texture2D(tex, gl_TexCoord[0].st + offset);
gl_FragColor += texture2D(tex, gl_TexCoord[0].st - offset);
gl_FragColor = normalize(gl_FragColor) + 0.5*gl_FragColor;
gl_FragColor *= 0.56;
//gl_FragColor = sin(gl_FragColor*3.0);
gl_FragColor.a = 1.0;
}

5
resources/myHBlurShader.vert

@ -0,0 +1,5 @@
void main( void ) {
gl_TexCoord[0] = gl_MultiTexCoord0;
gl_Position = gl_Vertex;
}

2
resources/myTeaShader.frag

@ -4,6 +4,6 @@ uniform int steps;
void main( void ) { void main( void ) {
gl_FragColor.rgb = sin(3.0*sin(normalize(color.rgb) + vec3(steps)*vec3(0.01, 0.017, 0.0093)))*0.5+0.5; gl_FragColor.rgb = sin(3.0*sin(normalize(color.rgb) + vec3(steps)*vec3(0.01, 0.017, 0.0093)))*0.5+0.5;
gl_FragColor.rgb *= 0.1; gl_FragColor.rgb *= 0.05;
gl_FragColor.a = 1.0; gl_FragColor.a = 1.0;
} }

3
resources/myTeaShader.vert

@ -2,6 +2,7 @@ varying vec4 color;
void main( void ) { void main( void ) {
gl_Position = ftransform(); gl_Position = ftransform();
gl_Position.xyz = gl_Position.xyz*0.6 - vec3(0.0, 0.0, 0.0); gl_Position.xyz = gl_Position.xyz*0.6;
gl_Position.x *= 600.0/800.0;
color = gl_Vertex; color = gl_Vertex;
} }

8
resources/myTextureShader.frag

@ -0,0 +1,8 @@
uniform sampler2D tex;
void main( void ) {
gl_FragColor = texture2D(tex, gl_TexCoord[0].st);
//gl_FragColor = sin(gl_FragColor*3.0);
gl_FragColor.a = 1.0;
}

5
resources/myTextureShader.vert

@ -0,0 +1,5 @@
void main( void ) {
gl_TexCoord[0] = gl_MultiTexCoord0;
gl_Position = gl_Vertex;
}

12
resources/myVBlurShader.frag

@ -0,0 +1,12 @@
uniform sampler2D tex;
vec2 offset = vec2(1.0/800.0, 0.0);
void main( void ) {
gl_FragColor = texture2D(tex, gl_TexCoord[0].st + offset);
gl_FragColor += texture2D(tex, gl_TexCoord[0].st - offset);
gl_FragColor = normalize(gl_FragColor) + 0.5*gl_FragColor;
gl_FragColor *= 0.56;
//gl_FragColor = sin(gl_FragColor*3.0);
gl_FragColor.a = 1.0;
}

5
resources/myVBlurShader.vert

@ -0,0 +1,5 @@
void main( void ) {
gl_TexCoord[0] = gl_MultiTexCoord0;
gl_Position = gl_Vertex;
}

9
shader.h

@ -16,7 +16,8 @@ class shader {
public: public:
shader(std::string vertex_shader_filename, std::string fragment_shader_filename) { shader(std::string vertex_shader_filename, std::string fragment_shader_filename) :
program(0), shaders() {
program = glCreateProgram(); program = glCreateProgram();
if(program == 0) { if(program == 0) {
throw std::runtime_error("Program couldn't be created"); throw std::runtime_error("Program couldn't be created");
@ -91,6 +92,12 @@ public:
glUniform4i(glGetUniformLocation(program, name), x, y, z, w); glUniform4i(glGetUniformLocation(program, name), x, y, z, w);
} }
void set_texture(const char* name, GLenum target, GLuint tex, int textureLocation) {
glActiveTexture(GL_TEXTURE0 + textureLocation);
glBindTexture(target, tex);
set_uniform(name, textureLocation);
}
private: private:
void read_shader(std::istream& file, GLenum type) { void read_shader(std::istream& file, GLenum type) {