oglc/src/main.c

143 lines
3.9 KiB
C
Raw Normal View History

2021-07-04 02:53:37 +01:00
#include "main.h"
#include "gfx.h"
2021-08-08 16:47:25 +01:00
#include "clock.h"
#include "random.h"
2021-07-04 02:53:37 +01:00
2021-08-06 19:25:52 +01:00
#include "sphere.h"
2021-08-07 15:19:22 +01:00
#include "cam.h"
#include "input.h"
2021-08-06 19:25:52 +01:00
2021-08-02 09:35:39 +01:00
const int WIDTH = 420;
const int HEIGHT = 420;
2022-06-21 00:41:52 +01:00
void updateUniforms(GLuint shaderProgram, float t);
2021-08-02 09:35:39 +01:00
SDL_Window *window;
2021-08-10 01:11:22 +01:00
struct Shaders shaders;
struct Textures textures;
2022-06-21 00:41:52 +01:00
struct Epoch epoch;
void initialise()
2021-07-04 02:53:37 +01:00
{
window = gfxInit(WIDTH, HEIGHT);
2021-08-09 18:15:43 +01:00
randomInit();
2021-07-10 16:16:01 +01:00
// initialise quad
initBuffers();
setVertexAttributes();
2021-07-05 08:51:55 +01:00
// compile shader programs
compileShaders(&shaders);
createTextures(WIDTH, HEIGHT, shaders, &textures);
}
2022-06-21 00:41:52 +01:00
void parseArgs(int argc, char* argv[], struct Epoch* e)
{
2022-06-21 00:41:52 +01:00
// check we have the right number of arguments
if (argc != 2)
{
fprintf(stderr, "usage: oglc TIMESPEED\n");
}
2022-06-25 22:09:19 +01:00
sscanf(argv[1], "%f", &(e->scale));
2022-06-21 00:41:52 +01:00
}
int main(int argc, char* argv[])
{
parseArgs(argc, argv, &epoch);
initialise();
2022-06-25 22:09:19 +01:00
float start = now();
int frames;
for (frames = 0; !checkQuit(); frames++)
2021-07-04 02:53:37 +01:00
{
GLuint shader;
2022-06-25 22:09:19 +01:00
float t = nowScaled(epoch);
// prepass
// TODO: write output to different texture than main output
shader = shaders.prepass;
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, textures.g0);
glUseProgram(shader);
2022-06-21 00:41:52 +01:00
updateUniforms(shader, t);
glDispatchCompute((GLuint)WIDTH, (GLuint)HEIGHT, 1);
// make sure we're finished writing to the texture before trying to read it
glMemoryBarrier(GL_ALL_BARRIER_BITS);
shader = shaders.lighting;
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, textures.target);
glUseProgram(shader);
2022-06-21 00:41:52 +01:00
updateUniforms(shader, t);
//int loc = glGetUniformLocation(shader, "_g0");
//glUniform1i(loc, textures.g0);
2021-08-02 09:35:39 +01:00
glDispatchCompute((GLuint)WIDTH, (GLuint)HEIGHT, 1);
2021-07-10 16:16:01 +01:00
// make sure we're finished writing to the texture before trying to read it
glMemoryBarrier(GL_SHADER_IMAGE_ACCESS_BARRIER_BIT);
2022-06-21 00:41:52 +01:00
// TODO: frame blending
//
// before we get to our normal rendering pass we need to blend our samples
// across multiple frames. to do this, we should maintain an accumulation
// buffer where we can store pixel data while a new frame is being generated.
// this can be a collection of two buffers, where one is written to and the
// other is read from. to render a new frame, the newly sampled raw frame can
// be combined with data from the previous frame. by repeatedly taking the
// average over a large number of frames a cleaner image can be generated.
// this is most effective for static images, and will produce motion blur on
// a moving image.
2021-07-10 16:16:01 +01:00
// normal drawing pass
shader = shaders.quad;
glUseProgram(shader);
2021-07-24 01:31:35 +01:00
// bind texture written to by compute stage to 2d target
2021-07-05 08:51:55 +01:00
glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, 0);
2021-07-10 16:16:01 +01:00
// swip swap
2021-07-05 01:05:37 +01:00
SDL_GL_SwapWindow(window);
2021-07-04 02:53:37 +01:00
}
2022-06-25 22:09:19 +01:00
float elapsed = now()-start;
2021-08-13 20:03:19 +01:00
printf("%d frames in %fs [%f fps]\n",
frames,
elapsed,
(float)frames/elapsed);
2021-07-04 02:53:37 +01:00
return 0;
}
2022-06-21 00:41:52 +01:00
void updateUniforms(GLuint shaderProgram, float t)
2021-08-02 09:35:39 +01:00
{
2021-08-08 16:47:25 +01:00
// update random values
vec4 seed =
{
randomFloat(),
randomFloat(),
randomFloat(),
randomFloat()
};
int loc = glGetUniformLocation(shaderProgram, "_seed");
glUniform4fv(loc, 1, seed);
2021-08-02 09:35:39 +01:00
float sin_t = sin(t);
2021-08-10 01:11:22 +01:00
loc = glGetUniformLocation(shaderProgram, "_t");
glUniform4f(loc, t, sin_t, (1.0 + sin_t)*0.5, 0.0f);
2021-08-02 09:35:39 +01:00
2021-08-10 01:11:22 +01:00
// update camera
2021-08-07 15:19:22 +01:00
float aspect = (float)WIDTH/(float)HEIGHT;
2022-06-21 00:41:52 +01:00
updateCameraUniforms(shaderProgram, aspect, t);
2021-08-06 19:25:52 +01:00
2021-08-10 01:11:22 +01:00
// make and update spheres
2023-02-26 03:26:42 +00:00
const int sphereCount = 25;
2021-08-06 19:25:52 +01:00
struct Sphere spheres[sphereCount];
2022-06-21 00:41:52 +01:00
makeSpheres(spheres, sphereCount, t);
2021-08-06 19:25:52 +01:00
updateSphereUniforms(shaderProgram, spheres, sphereCount);
2021-08-02 09:35:39 +01:00
}