diff --git a/.vscode/settings.json b/.vscode/settings.json new file mode 100644 index 0000000..e47cdf8 --- /dev/null +++ b/.vscode/settings.json @@ -0,0 +1,73 @@ +{ + "files.associations": { + "string": "cpp", + "cctype": "cpp", + "clocale": "cpp", + "cmath": "cpp", + "cstdarg": "cpp", + "cstddef": "cpp", + "cstdio": "cpp", + "cstdlib": "cpp", + "cstring": "cpp", + "ctime": "cpp", + "cwchar": "cpp", + "cwctype": "cpp", + "any": "cpp", + "array": "cpp", + "atomic": "cpp", + "hash_map": "cpp", + "bit": "cpp", + "*.tcc": "cpp", + "charconv": "cpp", + "chrono": "cpp", + "compare": "cpp", + "complex": "cpp", + "concepts": "cpp", + "condition_variable": "cpp", + "cstdint": "cpp", + "deque": "cpp", + "list": "cpp", + "map": "cpp", + "unordered_map": "cpp", + "vector": "cpp", + "exception": "cpp", + "algorithm": "cpp", + "functional": "cpp", + "iterator": "cpp", + "memory": "cpp", + "memory_resource": "cpp", + "numeric": "cpp", + "optional": "cpp", + "random": "cpp", + "ratio": "cpp", + "string_view": "cpp", + "system_error": "cpp", + "tuple": "cpp", + "type_traits": "cpp", + "utility": "cpp", + "format": "cpp", + "fstream": "cpp", + "initializer_list": "cpp", + "iomanip": "cpp", + "iosfwd": "cpp", + "iostream": "cpp", + "istream": "cpp", + "limits": "cpp", + "mutex": "cpp", + "new": "cpp", + "numbers": "cpp", + "ostream": "cpp", + "semaphore": "cpp", + "span": "cpp", + "sstream": "cpp", + "stdexcept": "cpp", + "stdfloat": "cpp", + "stop_token": "cpp", + "streambuf": "cpp", + "text_encoding": "cpp", + "thread": "cpp", + "cinttypes": "cpp", + "typeinfo": "cpp", + "variant": "cpp" + } +} \ No newline at end of file diff --git a/Makefile b/Makefile index 098c37b..3f9c45e 100644 --- a/Makefile +++ b/Makefile @@ -1,5 +1,5 @@ windows: - g++ main.cpp -lmingw32 -lSDL2main -lSDL2 -lSDL2_image -lopengl32 -mwindows -o shaders + g++ *.cpp -lmingw32 -lSDL2main -lSDL2 -lopengl32 -mwindows -o shaders linux: - g++ main.cpp -lSDL2 -lSDL2_image -lGL -o shaders + g++ -g *.cpp -lSDL2 -lGL -o shaders diff --git a/jshader.cpp b/jshader.cpp new file mode 100644 index 0000000..06ea620 --- /dev/null +++ b/jshader.cpp @@ -0,0 +1,229 @@ +#include "jshader.h" + +#include + +#ifdef __APPLE__ +#include "CoreFoundation/CoreFoundation.h" +#include + +#if ESSENTIAL_GL_PRACTICES_SUPPORT_GL3 +#include +#else +#include +#endif //!ESSENTIAL_GL_PRACTICES_SUPPORT_GL3 +#else +#include +#include +#endif + +namespace shader +{ + SDL_Window *win = nullptr; + SDL_Renderer *renderer = nullptr; + GLuint programId = 0; + SDL_Texture* backBuffer = nullptr; + SDL_Point win_size = {640, 480}; + SDL_Point tex_size = {320, 240}; + bool usingOpenGL; + + #ifndef __APPLE__ + + // I'm avoiding the use of GLEW or some extensions handler, but that + // doesn't mean you should... + PFNGLCREATESHADERPROC glCreateShader; + PFNGLSHADERSOURCEPROC glShaderSource; + PFNGLCOMPILESHADERPROC glCompileShader; + PFNGLGETSHADERIVPROC glGetShaderiv; + PFNGLGETSHADERINFOLOGPROC glGetShaderInfoLog; + PFNGLDELETESHADERPROC glDeleteShader; + PFNGLATTACHSHADERPROC glAttachShader; + PFNGLCREATEPROGRAMPROC glCreateProgram; + PFNGLLINKPROGRAMPROC glLinkProgram; + PFNGLVALIDATEPROGRAMPROC glValidateProgram; + PFNGLGETPROGRAMIVPROC glGetProgramiv; + PFNGLGETPROGRAMINFOLOGPROC glGetProgramInfoLog; + PFNGLUSEPROGRAMPROC glUseProgram; + + bool initGLExtensions() { + glCreateShader = (PFNGLCREATESHADERPROC)SDL_GL_GetProcAddress("glCreateShader"); + glShaderSource = (PFNGLSHADERSOURCEPROC)SDL_GL_GetProcAddress("glShaderSource"); + glCompileShader = (PFNGLCOMPILESHADERPROC)SDL_GL_GetProcAddress("glCompileShader"); + glGetShaderiv = (PFNGLGETSHADERIVPROC)SDL_GL_GetProcAddress("glGetShaderiv"); + glGetShaderInfoLog = (PFNGLGETSHADERINFOLOGPROC)SDL_GL_GetProcAddress("glGetShaderInfoLog"); + glDeleteShader = (PFNGLDELETESHADERPROC)SDL_GL_GetProcAddress("glDeleteShader"); + glAttachShader = (PFNGLATTACHSHADERPROC)SDL_GL_GetProcAddress("glAttachShader"); + glCreateProgram = (PFNGLCREATEPROGRAMPROC)SDL_GL_GetProcAddress("glCreateProgram"); + glLinkProgram = (PFNGLLINKPROGRAMPROC)SDL_GL_GetProcAddress("glLinkProgram"); + glValidateProgram = (PFNGLVALIDATEPROGRAMPROC)SDL_GL_GetProcAddress("glValidateProgram"); + glGetProgramiv = (PFNGLGETPROGRAMIVPROC)SDL_GL_GetProcAddress("glGetProgramiv"); + glGetProgramInfoLog = (PFNGLGETPROGRAMINFOLOGPROC)SDL_GL_GetProcAddress("glGetProgramInfoLog"); + glUseProgram = (PFNGLUSEPROGRAMPROC)SDL_GL_GetProcAddress("glUseProgram"); + + return glCreateShader && glShaderSource && glCompileShader && glGetShaderiv && + glGetShaderInfoLog && glDeleteShader && glAttachShader && glCreateProgram && + glLinkProgram && glValidateProgram && glGetProgramiv && glGetProgramInfoLog && + glUseProgram; + } + + #endif + + GLuint compileShader(const char* source, GLuint shaderType) { + // Create ID for shader + GLuint result = glCreateShader(shaderType); + // Add define depending on shader type + const char *sources[2] = { shaderType==GL_VERTEX_SHADER?"#define VERTEX\n":"#define FRAGMENT\n", source }; + // Define shader text + glShaderSource(result, 2, sources, NULL); + // Compile shader + glCompileShader(result); + + //Check vertex shader for errors + GLint shaderCompiled = GL_FALSE; + glGetShaderiv( result, GL_COMPILE_STATUS, &shaderCompiled ); + if( shaderCompiled != GL_TRUE ) { + std::cout << "Error en la compilación: " << result << "!" << std::endl; + GLint logLength; + glGetShaderiv(result, GL_INFO_LOG_LENGTH, &logLength); + if (logLength > 0) + { + GLchar *log = (GLchar*)malloc(logLength); + glGetShaderInfoLog(result, logLength, &logLength, log); + std::cout << "Shader compile log:" << log << std::endl; + free(log); + } + glDeleteShader(result); + result = 0; +// } else { +// std::cout << "Shader compilado correctamente. Id = " << result << std::endl; + } + return result; + } + + GLuint compileProgram(const char* vertexShaderSource, const char* fragmentShaderSource) { + GLuint programId = 0; + GLuint vtxShaderId, fragShaderId; + + programId = glCreateProgram(); + + vtxShaderId = compileShader(vertexShaderSource, GL_VERTEX_SHADER); + fragShaderId = compileShader(fragmentShaderSource?fragmentShaderSource:vertexShaderSource, GL_FRAGMENT_SHADER); + + if(vtxShaderId && fragShaderId) { + // Associate shader with program + glAttachShader(programId, vtxShaderId); + glAttachShader(programId, fragShaderId); + glLinkProgram(programId); + glValidateProgram(programId); + + // Check the status of the compile/link + GLint logLen; + glGetProgramiv(programId, GL_INFO_LOG_LENGTH, &logLen); + if(logLen > 0) { + char* log = (char*) malloc(logLen * sizeof(char)); + // Show any errors as appropriate + glGetProgramInfoLog(programId, logLen, &logLen, log); + std::cout << "Prog Info Log: " << std::endl << log << std::endl; + free(log); + } + } + if(vtxShaderId) { + glDeleteShader(vtxShaderId); + } + if(fragShaderId) { + glDeleteShader(fragShaderId); + } + return programId; + } + + const bool init(SDL_Window* win, SDL_Texture* backBuffer, const char* vertexShader, const char* fragmentShader) + { + shader::win = win; + shader::renderer = SDL_GetRenderer(win); + shader::backBuffer = backBuffer; + SDL_GetWindowSize(win, &win_size.x, &win_size.y); + int access; + SDL_QueryTexture(backBuffer, NULL, &access, &tex_size.x, &tex_size.y); + if (access != SDL_TEXTUREACCESS_TARGET) + { + std::cout << "ERROR FATAL: La textura per al render ha de tindre SDL_TEXTUREACCESS_TARGET definit." << std::endl; + exit(1); + } + + SDL_RendererInfo rendererInfo; + SDL_GetRendererInfo(renderer, &rendererInfo); + + if(!strncmp(rendererInfo.name, "opengl", 6)) { + //std::cout << "Es OpenGL!" << std::endl; + #ifndef __APPLE__ + if (!initGLExtensions()) { + std::cout << "WARNING: No s'han pogut inicialitzar les extensions d'OpenGL!" << std::endl; + usingOpenGL = false; + return false; + } + #endif + // Compilar el shader y dejarlo listo para usar. + programId = compileProgram(vertexShader, fragmentShader); + //std::cout << "programId = " << programId << std::endl; + } else { + std::cout << "WARNING: El driver del renderer no es OpenGL." << std::endl; + usingOpenGL = false; + return false; + } + usingOpenGL = true; + return true; + } + + void render() + { + GLint oldProgramId; + // Guarrada para obtener el textureid (en driverdata->texture) + //Detach the texture + SDL_SetRenderDrawColor(renderer, 0, 0, 0, 255); + + SDL_SetRenderTarget(renderer, NULL); + SDL_RenderClear(renderer); + + if (usingOpenGL) { + SDL_GL_BindTexture(backBuffer, NULL, NULL); + if(programId != 0) { + glGetIntegerv(GL_CURRENT_PROGRAM,&oldProgramId); + glUseProgram(programId); + } + + GLfloat minx, miny, maxx, maxy; + GLfloat minu, maxu, minv, maxv; + + // Coordenadas de la ventana donde pintar. + minx = 0.0f; + miny = 0.0f; + maxx = tex_size.x; + maxy = tex_size.y; + + minu = 0.0f; + maxu = 1.0f; + minv = 0.0f; + maxv = 1.0f; + + glViewport(0, 0, win_size.x, win_size.y); + + glBegin(GL_TRIANGLE_STRIP); + glTexCoord2f(minu, minv); + glVertex2f(minx, miny); + glTexCoord2f(maxu, minv); + glVertex2f(maxx, miny); + glTexCoord2f(minu, maxv); + glVertex2f(minx, maxy); + glTexCoord2f(maxu, maxv); + glVertex2f(maxx, maxy); + glEnd(); + SDL_GL_SwapWindow(win); + + if(programId != 0) { + glUseProgram(oldProgramId); + } + } else { + SDL_RenderCopy(renderer, backBuffer, NULL, NULL); + SDL_RenderPresent(renderer); + } + } +} diff --git a/jshader.h b/jshader.h new file mode 100644 index 0000000..556f796 --- /dev/null +++ b/jshader.h @@ -0,0 +1,44 @@ +#pragma once + +#include + +// TIPS: +// ======================================================================= +// Abans de crear el renderer, cridar a la següent funció: +// +// SDL_SetHint(SDL_HINT_RENDER_DRIVER, "opengl"); +// +// Aixó li diu que volem un renderer que use especificament opengl. A més, +// al crear el renderer li tenim que dir que el volem que use acceeració +// per hardware, i que soporte render a textura. Per exemple: +// +// SDL_Renderer *ren = SDL_CreateRenderer(win, -1, SDL_RENDERER_ACCELERATED | +// SDL_RENDERER_TARGETTEXTURE); +// +// Per altra part, al crear la textura tenim que definir que puga ser target +// de renderitzat (SDL_TEXTUREACCESS_TARGET), per exemple: +// +// SDL_Texture *tex = SDL_CreateTexture(renderer, SDL_PIXELFORMAT_ARGB8888, +// SDL_TEXTUREACCESS_TARGET, 320, 240); +// +// Els shaders li'ls passem com una cadena, som nosaltres els que s'encarreguem +// de carregarlos de disc, amb fopen, ifstream, jfile o el que vullgues. +// Si els tens en un std::string, passa-li-la com "cadena.c_str()". +// +// Poden ser els dos el mateix arxiu, com fa libRetro, jo desde dins ja fique +// els defines necessaris. Si es el mateix arxiu, pots no ficar el quart paràmetre. +// +// Els shaders de libRetro no funcionen directament, hi ha que fer algunes modificacions. +// +// El pintat final de la teua escena l'has de fer com si "backBuffer" fora la pantalla. +// +// Ah! una cosa mes: al compilar, en Linux afegir "-lGL", en Windows afegir "-lopengl32". +// En Mac ni idea + +namespace shader +{ + const bool init(SDL_Window* win, SDL_Texture* backBuffer, + const char* vertexShader, const char* fragmentShader=nullptr); + + void render(); +} diff --git a/main.cpp b/main.cpp index 52281c5..1ac89c2 100644 --- a/main.cpp +++ b/main.cpp @@ -1,355 +1,44 @@ #include - #include #include #include - +#include "jshader.h" #include -#include -#ifdef __APPLE__ -#include "CoreFoundation/CoreFoundation.h" -#include - -#if ESSENTIAL_GL_PRACTICES_SUPPORT_GL3 -#include -#else -#include -#endif //!ESSENTIAL_GL_PRACTICES_SUPPORT_GL3 -#else -#include -#include -#endif - -const int WIN_WIDTH = 1024; -const int WIN_HEIGHT = 768; - -const int WORLD_WIDTH = 320; -const int WORLD_HEIGHT = 240; - -struct sprite { - float x; - float y; - float vx; - float vy; -}; - -const int MAX_SPRITES = 20; - -#ifndef __APPLE__ - -// I'm avoiding the use of GLEW or some extensions handler, but that -// doesn't mean you should... -PFNGLCREATESHADERPROC glCreateShader; -PFNGLSHADERSOURCEPROC glShaderSource; -PFNGLCOMPILESHADERPROC glCompileShader; -PFNGLGETSHADERIVPROC glGetShaderiv; -PFNGLGETSHADERINFOLOGPROC glGetShaderInfoLog; -PFNGLDELETESHADERPROC glDeleteShader; -PFNGLATTACHSHADERPROC glAttachShader; -PFNGLCREATEPROGRAMPROC glCreateProgram; -PFNGLLINKPROGRAMPROC glLinkProgram; -PFNGLVALIDATEPROGRAMPROC glValidateProgram; -PFNGLGETPROGRAMIVPROC glGetProgramiv; -PFNGLGETPROGRAMINFOLOGPROC glGetProgramInfoLog; -PFNGLUSEPROGRAMPROC glUseProgram; - -bool initGLExtensions() { - glCreateShader = (PFNGLCREATESHADERPROC)SDL_GL_GetProcAddress("glCreateShader"); - glShaderSource = (PFNGLSHADERSOURCEPROC)SDL_GL_GetProcAddress("glShaderSource"); - glCompileShader = (PFNGLCOMPILESHADERPROC)SDL_GL_GetProcAddress("glCompileShader"); - glGetShaderiv = (PFNGLGETSHADERIVPROC)SDL_GL_GetProcAddress("glGetShaderiv"); - glGetShaderInfoLog = (PFNGLGETSHADERINFOLOGPROC)SDL_GL_GetProcAddress("glGetShaderInfoLog"); - glDeleteShader = (PFNGLDELETESHADERPROC)SDL_GL_GetProcAddress("glDeleteShader"); - glAttachShader = (PFNGLATTACHSHADERPROC)SDL_GL_GetProcAddress("glAttachShader"); - glCreateProgram = (PFNGLCREATEPROGRAMPROC)SDL_GL_GetProcAddress("glCreateProgram"); - glLinkProgram = (PFNGLLINKPROGRAMPROC)SDL_GL_GetProcAddress("glLinkProgram"); - glValidateProgram = (PFNGLVALIDATEPROGRAMPROC)SDL_GL_GetProcAddress("glValidateProgram"); - glGetProgramiv = (PFNGLGETPROGRAMIVPROC)SDL_GL_GetProcAddress("glGetProgramiv"); - glGetProgramInfoLog = (PFNGLGETPROGRAMINFOLOGPROC)SDL_GL_GetProcAddress("glGetProgramInfoLog"); - glUseProgram = (PFNGLUSEPROGRAMPROC)SDL_GL_GetProcAddress("glUseProgram"); - - return glCreateShader && glShaderSource && glCompileShader && glGetShaderiv && - glGetShaderInfoLog && glDeleteShader && glAttachShader && glCreateProgram && - glLinkProgram && glValidateProgram && glGetProgramiv && glGetProgramInfoLog && - glUseProgram; -} - -#endif - -GLuint compileShader(const char* source, GLuint shaderType) { - //std::cout << "Compilando shader:" << std::endl << source << std::endl; - // Create ID for shader - GLuint result = glCreateShader(shaderType); - - const char *sources[2] = { shaderType==GL_VERTEX_SHADER?"#define VERTEX\n":"#define FRAGMENT\n", source }; - - // Define shader text - glShaderSource(result, 2, sources, NULL); - // Compile shader - glCompileShader(result); - - //Check vertex shader for errors - GLint shaderCompiled = GL_FALSE; - glGetShaderiv( result, GL_COMPILE_STATUS, &shaderCompiled ); - if( shaderCompiled != GL_TRUE ) { - std::cout << "Error en la compilación: " << result << "!" << std::endl; - GLint logLength; - glGetShaderiv(result, GL_INFO_LOG_LENGTH, &logLength); - if (logLength > 0) - { - GLchar *log = (GLchar*)malloc(logLength); - glGetShaderInfoLog(result, logLength, &logLength, log); - std::cout << "Shader compile log:" << log << std::endl; - free(log); - } - glDeleteShader(result); - result = 0; - } else { - std::cout << "Shader compilado correctamente. Id = " << result << std::endl; - } - return result; -} - -GLuint compileProgram(const char* vtxFile, const char* fragFile) { - GLuint programId = 0; - GLuint vtxShaderId, fragShaderId; - - programId = glCreateProgram(); - - std::ifstream f(vtxFile); - std::string source((std::istreambuf_iterator(f)), - std::istreambuf_iterator()); - - vtxShaderId = compileShader(source.c_str(), GL_VERTEX_SHADER); - - f=std::ifstream(fragFile); - source=std::string((std::istreambuf_iterator(f)), - std::istreambuf_iterator()); - fragShaderId = compileShader(source.c_str(), GL_FRAGMENT_SHADER); - - if(vtxShaderId && fragShaderId) { - // Associate shader with program - glAttachShader(programId, vtxShaderId); - glAttachShader(programId, fragShaderId); - glLinkProgram(programId); - glValidateProgram(programId); - - // Check the status of the compile/link - GLint logLen; - glGetProgramiv(programId, GL_INFO_LOG_LENGTH, &logLen); - if(logLen > 0) { - char* log = (char*) malloc(logLen * sizeof(char)); - // Show any errors as appropriate - glGetProgramInfoLog(programId, logLen, &logLen, log); - std::cout << "Prog Info Log: " << std::endl << log << std::endl; - free(log); - } - } - if(vtxShaderId) { - glDeleteShader(vtxShaderId); - } - if(fragShaderId) { - glDeleteShader(fragShaderId); - } - return programId; -} - -void presentBackBuffer(SDL_Renderer *renderer, SDL_Window* win, SDL_Texture* backBuffer, GLuint programId) { - GLint oldProgramId; - // Guarrada para obtener el textureid (en driverdata->texture) - //Detach the texture - SDL_SetRenderDrawColor(renderer, 0, 0, 0, 255); - - SDL_SetRenderTarget(renderer, NULL); - SDL_RenderClear(renderer); - - SDL_GL_BindTexture(backBuffer, NULL, NULL); - if(programId != 0) { - glGetIntegerv(GL_CURRENT_PROGRAM,&oldProgramId); - glUseProgram(programId); - } - - GLfloat minx, miny, maxx, maxy; - GLfloat minu, maxu, minv, maxv; - - // Coordenadas de la ventana donde pintar. - minx = 0.0f; - miny = 0.0f; - maxx = WORLD_WIDTH; - maxy = WORLD_HEIGHT; - - minu = 0.0f; - maxu = 1.0f; - minv = 0.0f; - maxv = 1.0f; - - glViewport(0, 0, WIN_WIDTH, WIN_HEIGHT); - - glBegin(GL_TRIANGLE_STRIP); - glTexCoord2f(minu, minv); - glVertex2f(minx, miny); - glTexCoord2f(maxu, minv); - glVertex2f(maxx, miny); - glTexCoord2f(minu, maxv); - glVertex2f(minx, maxy); - glTexCoord2f(maxu, maxv); - glVertex2f(maxx, maxy); - glEnd(); - SDL_GL_SwapWindow(win); - - if(programId != 0) { - glUseProgram(oldProgramId); - } -} - -#ifdef __APPLE__ -void initializeFileSystem() { - CFBundleRef mainBundle = CFBundleGetMainBundle(); - CFURLRef resourcesURL = CFBundleCopyResourcesDirectoryURL(mainBundle); - char path[PATH_MAX]; - if (!CFURLGetFileSystemRepresentation(resourcesURL, TRUE, (UInt8 *)path, PATH_MAX)) - { - std::cerr << "Couldn't get file system representation! " << std::endl; - } - CFRelease(resourcesURL); - chdir(path); -} -#endif - -int main(int argc, char **argv){ - - if (argc < 2) { - std::cerr << "Uso: shaders [vertex shader] [fragment shader]" << "\n"; - std::cerr << " shaders [unique shader]" << "\n"; - return 1; - } - char *vertex_shader = argv[1]; - char *fragment_shader = argc<3 ? vertex_shader : argv[2]; - - GLuint programId; - -#ifdef __APPLE__ - initializeFileSystem(); -#endif - - if (SDL_Init(SDL_INIT_EVERYTHING | SDL_VIDEO_OPENGL) != 0){ - std::cerr << "SDL_Init failed: " << SDL_GetError() << "\n"; - return 1; - } - - SDL_Window *win = SDL_CreateWindow("Custom shader with SDL2 renderer!", SDL_WINDOWPOS_CENTERED, - SDL_WINDOWPOS_CENTERED, WIN_WIDTH, WIN_HEIGHT, 0); +#define WIDTH 384 +#define HEIGHT 240 +int main(int argc, char **argv) +{ + SDL_Init(SDL_INIT_EVERYTHING); + SDL_Window *win = SDL_CreateWindow("Shaders i tal", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, WIDTH*3, HEIGHT*3, 0); SDL_SetHint(SDL_HINT_RENDER_DRIVER, "opengl"); + SDL_Renderer *renderer = SDL_CreateRenderer(win, -1, SDL_RENDERER_ACCELERATED | SDL_RENDERER_TARGETTEXTURE); + SDL_Texture *texTarget = SDL_CreateTexture(renderer, SDL_PIXELFORMAT_ARGB8888, SDL_TEXTUREACCESS_TARGET, WIDTH, HEIGHT); - SDL_Renderer *renderer = SDL_CreateRenderer(win, -1, - SDL_RENDERER_ACCELERATED | SDL_RENDERER_TARGETTEXTURE); + std::ifstream f("crtpi.glsl"); + std::string source((std::istreambuf_iterator(f)), std::istreambuf_iterator()); - SDL_RendererInfo rendererInfo; - SDL_GetRendererInfo(renderer, &rendererInfo); + shader::init(win, texTarget, source.c_str()); - if(!strncmp(rendererInfo.name, "opengl", 6)) { - std::cout << "Es OpenGL!" << std::endl; -#ifndef __APPLE__ - // If you want to use GLEW or some other GL extension handler, do it here! - if (!initGLExtensions()) { - std::cout << "Couldn't init GL extensions!" << std::endl; - SDL_Quit(); - exit(-1); + // Carreguem una imatge pa ficar algo + SDL_Texture *bmpTex = SDL_CreateTextureFromSurface(renderer, SDL_LoadBMP("pang.bmp")); + + bool should_exit = false; + + while (!should_exit) + { + SDL_Event e; + while ( SDL_PollEvent(&e) ) { + if ( e.type == SDL_QUIT || ( e.type == SDL_KEYDOWN && e.key.keysym.sym == SDLK_ESCAPE ) ) { should_exit = true; } } -#endif - // Compilar el shader y dejarlo listo para usar. - programId = compileProgram(vertex_shader, fragment_shader); - std::cout << "programId = " << programId << std::endl; - } - //Put your own bmp image here - SDL_Surface *bmpSurf = IMG_Load("image.png"); - SDL_Texture *bmpTex = SDL_CreateTextureFromSurface(renderer, bmpSurf); - SDL_FreeSurface(bmpSurf); - - //Make a target texture to render too - SDL_Texture *texTarget = SDL_CreateTexture(renderer, SDL_PIXELFORMAT_RGBA8888, - SDL_TEXTUREACCESS_TARGET, WORLD_WIDTH, WORLD_HEIGHT); - - int done = 0; - int useShader = 0; - SDL_Rect targetRect; - - targetRect.x = 0; targetRect.y=0; targetRect.w=32; targetRect.h=32; - - struct sprite sprites[MAX_SPRITES]; - - for(int i=0;i < MAX_SPRITES;++i) { - sprites[i].x = (float) (rand() % (WORLD_WIDTH - targetRect.w)); - sprites[i].y = (float) (rand() % (WORLD_HEIGHT - targetRect.h)); - sprites[i].vx = (float) (rand() % 5 / 10.0f) - 0.2f; - sprites[i].vy = (float) (rand() % 5 / 10.0f) - 0.2f; - } - - // Voy a poner el fondo blanco para que se vea el shader - SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255); - - while ( ! done ) { - //Render to the texture - SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255); SDL_SetRenderTarget(renderer, texTarget); - SDL_RenderClear(renderer); - - // Pintamos MAX_SPRITES UWOLes - struct sprite* spr; - for(int i=0;i < MAX_SPRITES;++i) { - spr = &(sprites[i]); - spr->x += spr->vx; - if(spr->x < 0) { - spr->x = 0; - spr->vx *= -1; - } - if(spr->x > WORLD_WIDTH - targetRect.w) { - spr->x = (float) (WORLD_WIDTH - targetRect.w); - spr->vx *= -1; - } - spr->y += spr->vy; - if(spr->y < 0) { - spr->y = 0; - spr->vy *= -1; - } - if(spr->y > WORLD_HEIGHT - targetRect.h) { - spr->y = (float) (WORLD_HEIGHT - targetRect.h); - spr->vy *= -1; - } - - targetRect.x = (int)spr->x; - targetRect.y = (int)spr->y; - - SDL_RenderCopy(renderer, bmpTex, NULL, &targetRect); - } - - presentBackBuffer(renderer, win, texTarget, programId); - - /* This could go in a separate function */ - SDL_Event event; - while ( SDL_PollEvent(&event) ) { - if ( event.type == SDL_QUIT ) { - done = 1; - } - if ( event.type == SDL_KEYDOWN ) { - if ( event.key.keysym.sym == SDLK_SPACE ) { - useShader ^= 1; - std::cout << "useShader = " << (useShader ? "true" : "false") << std::endl; - } - if ( event.key.keysym.sym == SDLK_ESCAPE ) { - done = 1; - } - } - } + SDL_RenderCopy(renderer, bmpTex, NULL, NULL); + + shader::render(); } - SDL_DestroyTexture(texTarget); - SDL_DestroyTexture(bmpTex); - SDL_DestroyRenderer(renderer); - SDL_DestroyWindow(win); SDL_Quit(); return 0; } \ No newline at end of file diff --git a/pang.bmp b/pang.bmp new file mode 100644 index 0000000..c017e9a Binary files /dev/null and b/pang.bmp differ