src/shader.c

Tue, 26 Mar 2024 20:37:21 +0100

author
Mike Becker <universe@uap-core.de>
date
Tue, 26 Mar 2024 20:37:21 +0100
changeset 44
b3da4096c607
parent 41
df81d493716e
child 50
d8d2e4817db1
permissions
-rw-r--r--

create own compilation unit for GL context - fixes shader not being created per context

     1 /*
     2  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
     3  * Copyright 2023 Mike Becker. All rights reserved.
     4  *
     5  * Redistribution and use in source and binary forms, with or without
     6  * modification, are permitted provided that the following conditions are met:
     7  *
     8  *   1. Redistributions of source code must retain the above copyright
     9  *      notice, this list of conditions and the following disclaimer.
    10  *
    11  *   2. Redistributions in binary form must reproduce the above copyright
    12  *      notice, this list of conditions and the following disclaimer in the
    13  *      documentation and/or other materials provided with the distribution.
    14  *
    15  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
    16  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
    17  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
    18  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
    19  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
    20  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
    21  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
    22  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
    23  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
    24  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
    25  * POSSIBILITY OF SUCH DAMAGE.
    26  */
    28 #include "ascension/shader.h"
    29 #include "ascension/files.h"
    30 #include "ascension/error.h"
    32 #include <GL/glew.h>
    33 #include <string.h>
    35 AscShaderSprite ASC_SHADER_SPRITE;
    38 AscShader asc_shader_compile(unsigned int type,
    39                              char const *code,
    40                              int length) {
    41     GLuint id = glCreateShader(type);
    42     if (id == 0) {
    43         asc_error("glCreateShader failed");
    44         return (AscShader) {0};
    45     }
    47     GLint success;
    48     glShaderSource(id, 1, &code, &length);
    49     glCompileShader(id);
    50     glGetShaderiv(id, GL_COMPILE_STATUS, &success);
    51     if (success) {
    52         asc_dprintf("Shader %u compiled", id);
    53         return (AscShader) {id};
    54     } else {
    55         char *log = malloc(1024);
    56         glGetShaderInfoLog(id, 1024, NULL, log);
    57         glDeleteShader(id);
    58         asc_error(log);
    59         free(log);
    60         return (AscShader) {0};
    61     }
    62 }
    64 AscShader asc_shader_compilef(unsigned int type,
    65                               char const *filename) {
    66     asc_file code = asc_file_mmap_rdonly(filename);
    67     if (code.ptr == NULL) {
    68         asc_error("Mapping shader file into memory failed");
    69         return (AscShader) {0};
    70     }
    71     AscShader ret = asc_shader_compile(type, code.ptr, code.length);
    72     asc_file_unmap(code);
    73     return ret;
    74 }
    76 AscShaderProgram asc_shader_link(AscShader vertex,
    77                                  AscShader fragment) {
    78     if (vertex.id == 0 || fragment.id == 0) {
    79         asc_dprintf("Skip linking shader program - shaders have not been loaded correctly.");
    80         return (AscShaderProgram) {0};
    81     }
    83     GLint success;
    84     GLint id = glCreateProgram();
    85     if (id <= 0) {
    86         asc_error("glCreateProgram failed");
    87         return (AscShaderProgram) {0};
    88     }
    89     glAttachShader(id, vertex.id);
    90     glAttachShader(id, fragment.id);
    91     glLinkProgram(id);
    92     glGetProgramiv(id, GL_LINK_STATUS, &success);
    93     glDetachShader(id, vertex.id);
    94     glDetachShader(id, fragment.id);
    95     if (success) {
    96         asc_dprintf("Shader Program %u linked (vtf: %u, frag: %u)", id, vertex.id, fragment.id);
    97         AscShaderProgram prog;
    98         prog.id = id;
    99         prog.model = glGetUniformLocation(id, "model");
   100         prog.view = glGetUniformLocation(id, "view");
   101         prog.projection = glGetUniformLocation(id, "projection");
   102         return prog;
   103     } else {
   104         char *log = malloc(1024);
   105         glGetProgramInfoLog(id, 1024, NULL, log);
   106         glDeleteShader(id);
   107         asc_error(log);
   108         free(log);
   109         return (AscShaderProgram) {0};
   110     }
   111 }
   113 void asc_shader_destroy(AscShader shader) {
   114     if (shader.id > 0) {
   115         asc_dprintf("Delete Shader %u", shader.id);
   116         glDeleteShader(shader.id);
   117     }
   118     shader.id = 0;
   119 }
   121 void asc_shader_program_destroy(AscShaderProgram program) {
   122     if (program.id > 0) {
   123         asc_dprintf("Delete Shader Program %u", program.id);
   124         glDeleteProgram(program.id);
   125     }
   126     program.id = 0;
   127 }
   129 AscShaderProgram asc_shader_easy_compile_and_link(
   130         char const *vtxName, char const *fragName) {
   131     AscShader font_vtx = asc_shader_compilef(GL_VERTEX_SHADER, vtxName);
   132     AscShader font_frag = asc_shader_compilef(GL_FRAGMENT_SHADER, fragName);
   133     AscShaderProgram prog = asc_shader_link(font_vtx, font_frag);
   134     asc_shader_destroy(font_vtx);
   135     asc_shader_destroy(font_frag);
   136     return prog;
   137 }

mercurial