revolver

Unnamed repository; edit this file 'description' to name the repository.
Log | Files | Refs

uniform.c (5968B)


      1 //////////////////////////////////////////////////////////////////
      2 // uniform.c
      3 
      4 #include "revolver_inc.h"
      5 #include "revolver_inc.c"
      6 
      7 //////////////////////////////////////////////////////////////////
      8 // data
      9 
     10 f32 v_data[] = {
     11      0.0f,  0.5f, 1, 0, 0,
     12     -0.5f, -0.5f, 0, 1, 0,
     13      0.5f, -0.5f, 0, 0, 1,
     14 };
     15 
     16 rv_str8 v_src = S("#version 330 core\n" rv_strify(
     17     layout(location = 0) in vec2 a_pos;
     18     layout(location = 1) in vec3 a_color;
     19     precision mediump float;
     20     uniform mat4 u_model;
     21     out vec3 f_color;
     22     void main()
     23     {
     24         gl_Position = u_model * vec4(a_pos, 0.0, 1.0);
     25         f_color = a_color;
     26     }
     27 ));
     28 
     29 rv_str8 f_src = S("#version 330 core\n" rv_strify(
     30     precision mediump float;
     31     in vec3 f_color;
     32     out vec4 frag_color;
     33     uniform vec3 u_color;
     34     void main()
     35     {
     36     frag_color = vec4(u_color * f_color, 1.0);
     37     }
     38 ));
     39 
     40 //////////////////////////////////////////////////////////////////
     41 
     42 int main(void) {
     43     rv_window_desc_t desc = {.name = S("App"), .attach_render = true};
     44     rv_window_handle_t* window = rv_create_window(desc);
     45 
     46     rv_arena* arena = rv_arena_alloc();
     47     rv_render_pass_list_t rpass_list = {0};
     48 
     49     // make render objects
     50     rv_vbo_t*      vbo      = rv_push_compound(arena, rv_vbo_t,     {.data   = v_data,     .size = sizeof(v_data)});
     51     rv_shader_t*   vertex   = rv_push_compound(arena, rv_shader_t,  {.source = v_src,      .type = RV_SHADER_TYPE_VERTEX});
     52     rv_shader_t*   fragment = rv_push_compound(arena, rv_shader_t,  {.source = f_src,      .type = RV_SHADER_TYPE_FRAGMENT});
     53     rv_pipeline_t* pip      = rv_push(arena, rv_pipeline_t);
     54 
     55     // construct pipeline
     56     rv_pipeline_push_shader(arena, pip, vertex);
     57     rv_pipeline_push_shader(arena, pip, fragment);
     58     rv_pipeline_push_vattr(arena, pip, RV_VATTR_TYPE_FLOAT2);
     59     rv_pipeline_push_vattr(arena, pip, RV_VATTR_TYPE_FLOAT3);
     60     rv_uniform_t* u_color = rv_pipeline_push_uniform(arena, pip, S("u_color"), RV_UNIFORM_VEC3);
     61     rv_uniform_t* u_model = rv_pipeline_push_uniform(arena, pip, S("u_model"), RV_UNIFORM_MAT4);
     62 
     63     // instructions to create render objects
     64     rv_command_list_t create_instructions = {0};
     65     rv_cmd_push_obj(arena, &create_instructions, RV_COMMAND_OBJ_VERTEX,   RV_RENDER_OBJ_OP_CREATE, vbo);
     66     rv_cmd_push_obj(arena, &create_instructions, RV_COMMAND_OBJ_SHADER,   RV_RENDER_OBJ_OP_CREATE, vertex);
     67     rv_cmd_push_obj(arena, &create_instructions, RV_COMMAND_OBJ_SHADER,   RV_RENDER_OBJ_OP_CREATE, fragment);
     68     rv_cmd_push_obj(arena, &create_instructions, RV_COMMAND_OBJ_PIPELINE, RV_RENDER_OBJ_OP_CREATE, pip);
     69 
     70     // instructions to render
     71     rv_command_list_t render_instructions = {0};
     72     rv_cmd_push_obj(arena,  &render_instructions, RV_COMMAND_OBJ_PIPELINE, RV_RENDER_OBJ_OP_BIND, pip);
     73     rv_cmd_push_obj(arena,  &render_instructions, RV_COMMAND_OBJ_VERTEX,   RV_RENDER_OBJ_OP_BIND, vbo);
     74     rv_cmd_push_type(arena, &render_instructions, RV_COMMAND_DRAW)->draw.count = 3;
     75     rv_cmd_push_obj(arena,  &render_instructions, RV_COMMAND_OBJ_PIPELINE, RV_RENDER_OBJ_OP_BIND, NULL);
     76 
     77     // copy over create commands
     78     rv_render_pass_t* create_rpass = rv_render_push_render_pass(arena, &rpass_list);
     79     rv_render_copy_commands(arena, &create_rpass->commands, &create_instructions);
     80 
     81 
     82     while(1) {
     83         rv_temp_arena scratch = rv_scratch_begin(0, 0);
     84 
     85         // pick renderpass
     86         rv_render_pass_t* rpass = rv_render_push_render_pass(scratch.arena, &rpass_list);
     87 
     88         // process events
     89         for (rv_event_t* e = rv_get_events(scratch.arena, 0); e; e = e->next) {
     90             if (e->type == RV_EVENT_WINDOW_CLOSE) {
     91                 if (e->window_close == window) {
     92                     goto exit_program;
     93                 }
     94             }
     95             if (e->type == RV_EVENT_WINDOW_RESIZE) {
     96                 // set viewport
     97                 rv_command_t* viewport = rv_cmd_push_type(scratch.arena, &rpass->commands, RV_COMMAND_SET_VIEWPORT);
     98                 viewport->viewport = rv_v4(.xy = {0, 0}, .zw = rv_window_size(window));
     99             }
    100         }
    101 
    102 
    103         { // clear
    104             rv_command_t* clear = rv_cmd_push_type(scratch.arena, &rpass->commands, RV_COMMAND_CLEAR);
    105             rv_render_clear_desc_t* clear_desc = rv_render_push_clear_desc(scratch.arena, clear, RV_RENDER_CLEAR_FLAG_COLOR);
    106             clear_desc->color_v = rv_v4(0.1, 0.1, 0.1, 1.0);
    107         }
    108 
    109         { // draw custom shader
    110 
    111             // copy render commands
    112             rv_command_t* rcmd = rv_render_copy_commands(scratch.arena, &rpass->commands, &render_instructions);
    113 
    114             // find the pipeline command
    115             rv_command_t* pipeline_cmd = rcmd;
    116             for (; pipeline_cmd; pipeline_cmd = pipeline_cmd->next) {
    117                 if (rv_command_has_pipeline(pipeline_cmd, pip)) break;
    118             }
    119 
    120             if (pipeline_cmd) {
    121                 // add uniform updates
    122                 const f64 t = rv_time();
    123                 const f32 r = sinf(t) * 0.5f + 0.5f;
    124                 const f32 g = cosf(t * 6.f) * 0.5f + 0.5f;
    125                 const f32 b = sinf(t * 3.f) * 0.5f + 0.5f;
    126                 rv_cmd_insert_uniform_update(scratch.arena, &rpass->commands, pipeline_cmd, u_color, {.v_vec3 = rv_v3(r, g, b)});
    127 
    128                 const f32 st = sin(t);
    129                 rv_mat4 rot = rv_mat4_rotatev(t, RV_ZAXIS);
    130                 rv_mat4 scl = rv_mat4_scalev(rv_v3(st, st, st));
    131                 rv_mat4 model = rv_mat4_mul_list(2, scl, rot);
    132                 rv_command_t* update_u_model = rv_cmd_insert_type(scratch.arena, &rpass->commands, pipeline_cmd, RV_COMMAND_UNIFORM_UPDATE);
    133                 update_u_model->uniform_update.desc = u_model;
    134                 update_u_model->uniform_update.value.v_mat4 = model;
    135             }
    136         }
    137 
    138         if (window) { // render screen
    139             rv_window_render_commit(window, &rpass_list);
    140         }
    141         rv_scratch_end(scratch);
    142         rpass_list = (rv_render_pass_list_t){0};
    143     }
    144 exit_program:
    145 
    146     return 0;
    147 }