From 53ffb78a18e1fc2345ab8e53299ba576d40a5bd7 Mon Sep 17 00:00:00 2001 From: Andre Weissflog Date: Sun, 22 Sep 2024 14:02:48 +0200 Subject: [PATCH] emscripten samples bindings cleanup wip --- html5/bufferoffsets-emsc.c | 36 +++++-- html5/dyntex-emsc.c | 80 ++++++++------- html5/imgui-emsc.cc | 76 +++++++------- html5/inject-emsc.c | 66 ++++++------ html5/instancing-emsc.c | 46 +++++---- html5/mipmap-emsc.c | 66 ++++++------ html5/mrt-emsc.c | 193 +++++++++++++++++------------------- html5/noninterleaved-emsc.c | 42 ++++---- html5/offscreen-emsc.c | 142 ++++++++++++++++---------- 9 files changed, 398 insertions(+), 349 deletions(-) diff --git a/html5/bufferoffsets-emsc.c b/html5/bufferoffsets-emsc.c index 0a952d77..dd277d46 100644 --- a/html5/bufferoffsets-emsc.c +++ b/html5/bufferoffsets-emsc.c @@ -63,23 +63,41 @@ int main() { // create a shader to render 2D colored shapes sg_shader shd = sg_make_shader(&(sg_shader_desc){ + .attrs = { + [0].glsl_name = "pos", + [1].glsl_name = "color0", + }, .vertex_func.source = - "#version 300 es\n" - "layout(location=0) in vec2 pos;" - "layout(location=1) in vec3 color0;" - "out vec4 color;" + "attribute vec2 pos;" + "attribute vec3 color0;" + "varying vec4 color;" "void main() {" " gl_Position = vec4(pos, 0.5, 1.0);\n" " color = vec4(color0, 1.0);\n" "}\n", + // FIXME: for some reason using WebGL2 shaders causes corruption + //"#version 300 es\n" + //"in vec2 pos;" + //"in vec3 color0;" + //"out vec4 color;" + //"void main() {" + //" gl_Position = vec4(pos, 0.5, 1.0);\n" + //" color = vec4(color0, 1.0);\n" + //"}\n", .fragment_func.source = - "#version 300 es\n", "precision mediump float;\n" - "in vec4 color;\n" - "out vec4 frag_color;\n" + "varying vec4 color;\n" "void main() {\n" - " frag_color = color;\n" - "}\n" + " gl_FragColor = color;\n" + "}\n", + // FIXME! + //"#version 300 es\n", + //"precision mediump float;\n" + //"in vec4 color;\n" + //"out vec4 frag_color;\n" + //"void main() {\n" + //" frag_color = color;\n" + //"}\n" }); // a pipeline state object, default states are fine diff --git a/html5/dyntex-emsc.c b/html5/dyntex-emsc.c index b67e65df..71265bea 100644 --- a/html5/dyntex-emsc.c +++ b/html5/dyntex-emsc.c @@ -117,52 +117,50 @@ int main() { state.bind = (sg_bindings){ .vertex_buffers[0] = vbuf, .index_buffer = ibuf, - .fs = { - .images[0] = img, - .samplers[0] = smp, - } + .images[0] = img, + .samplers[0] = smp, }; // a shader to render textured cube sg_shader shd = sg_make_shader(&(sg_shader_desc){ + .vertex_func.source = + "#version 300 es\n" + "uniform mat4 mvp;\n" + "in vec4 position;\n" + "in vec4 color0;\n" + "in vec2 texcoord0;\n" + "out vec2 uv;" + "out vec4 color;" + "void main() {\n" + " gl_Position = mvp * position;\n" + " uv = texcoord0;\n" + " color = color0;\n" + "}\n", + .fragment_func.source = + "#version 300 es\n" + "precision mediump float;\n" + "uniform sampler2D tex;\n" + "in vec4 color;\n" + "in vec2 uv;\n" + "out vec4 frag_color;\n" + "void main() {\n" + " frag_color = texture(tex, uv) * color;\n" + "}\n", .attrs = { - [0].name = "position", - [1].name = "color0", - [2].name = "texcoord0" + [0].glsl_name = "position", + [1].glsl_name = "color0", + [2].glsl_name = "texcoord0" }, - .vs = { - .uniform_blocks[0] = { - .size = sizeof(vs_params_t), - .uniforms = { - [0] = { .name="mvp", .type=SG_UNIFORMTYPE_MAT4 } - } - }, - .source = - "uniform mat4 mvp;\n" - "attribute vec4 position;\n" - "attribute vec4 color0;\n" - "attribute vec2 texcoord0;\n" - "varying vec2 uv;" - "varying vec4 color;" - "void main() {\n" - " gl_Position = mvp * position;\n" - " uv = texcoord0;\n" - " color = color0;\n" - "}\n", + .uniform_blocks[0] = { + .stage = SG_SHADERSTAGE_VERTEX, + .size = sizeof(vs_params_t), + .glsl_uniforms = { + [0] = { .glsl_name = "mvp", .type = SG_UNIFORMTYPE_MAT4 } + } }, - .fs = { - .images[0].used = true, - .samplers[0].used = true, - .image_sampler_pairs[0] = { .used = true, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, - .source = - "precision mediump float;\n" - "uniform sampler2D tex;\n" - "varying vec4 color;\n" - "varying vec2 uv;\n" - "void main() {\n" - " gl_FragColor = texture2D(tex, uv) * color;\n" - "}\n" - } + .images[0].stage = SG_SHADERSTAGE_FRAGMENT, + .samplers[0].stage = SG_SHADERSTAGE_FRAGMENT, + .image_sampler_pairs[0] = { .stage = SG_SHADERSTAGE_FRAGMENT, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, }); // a pipeline-state-object for the textured cube @@ -209,13 +207,13 @@ static EM_BOOL draw(double time, void* userdata) { game_of_life_update(); // update the dynamic image - sg_update_image(state.bind.fs.images[0], &(sg_image_data){ .subimage[0][0] = SG_RANGE(pixels) }); + sg_update_image(state.bind.images[0], &(sg_image_data){ .subimage[0][0] = SG_RANGE(pixels) }); // draw pass sg_begin_pass(&(sg_pass){ .action = state.pass_action, .swapchain = emsc_swapchain() }); sg_apply_pipeline(state.pip); sg_apply_bindings(&state.bind); - sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, &SG_RANGE(vs_params)); + sg_apply_uniforms(0, &SG_RANGE(vs_params)); sg_draw(0, 36, 1); sg_end_pass(); sg_commit(); diff --git a/html5/imgui-emsc.cc b/html5/imgui-emsc.cc index 0dbadf12..344a5848 100644 --- a/html5/imgui-emsc.cc +++ b/html5/imgui-emsc.cc @@ -161,7 +161,7 @@ int main() { unsigned char* font_pixels; int font_width, font_height; io.Fonts->GetTexDataAsRGBA32(&font_pixels, &font_width, &font_height); - bind.fs.images[0] = sg_make_image({ + bind.images[0] = sg_make_image({ .width = font_width, .height = font_height, .pixel_format = SG_PIXELFORMAT_RGBA8, @@ -170,51 +170,51 @@ int main() { .size = size_t(font_width * font_height * 4) } }); - bind.fs.samplers[0] = sg_make_sampler({ + bind.samplers[0] = sg_make_sampler({ .wrap_u = SG_WRAP_CLAMP_TO_EDGE, .wrap_v = SG_WRAP_CLAMP_TO_EDGE, }); // shader object for imgui rendering sg_shader shd = sg_make_shader({ + .vertex_func.source = + "#version 300 es\n" + "uniform vec2 disp_size;\n" + "in vec2 position;\n" + "in vec2 texcoord0;\n" + "in vec4 color0;\n" + "out vec2 uv;\n" + "out vec4 color;\n" + "void main() {\n" + " gl_Position = vec4(((position/disp_size)-0.5)*vec2(2.0,-2.0), 0.5, 1.0);\n" + " uv = texcoord0;\n" + " color = color0;\n" + "}\n", + .fragment_func.source = + "#version 300 es\n" + "precision mediump float;" + "uniform sampler2D tex;\n" + "in vec2 uv;\n" + "in vec4 color;\n" + "out vec4 frag_color;\n" + "void main() {\n" + " frag_color = texture(tex, uv) * color;\n" + "}\n", .attrs = { - [0].name = "position", - [1].name = "texcoord0", - [2].name = "color0" + [0].glsl_name = "position", + [1].glsl_name = "texcoord0", + [2].glsl_name = "color0" }, - .vs = { - .uniform_blocks[0] = { - .size = sizeof(vs_params_t), - .uniforms = { - [0] = { .name="disp_size", .type=SG_UNIFORMTYPE_FLOAT2} - } - }, - .source = - "uniform vec2 disp_size;\n" - "attribute vec2 position;\n" - "attribute vec2 texcoord0;\n" - "attribute vec4 color0;\n" - "varying vec2 uv;\n" - "varying vec4 color;\n" - "void main() {\n" - " gl_Position = vec4(((position/disp_size)-0.5)*vec2(2.0,-2.0), 0.5, 1.0);\n" - " uv = texcoord0;\n" - " color = color0;\n" - "}\n", + .uniform_blocks[0] = { + .stage = SG_SHADERSTAGE_FRAGMENT, + .size = sizeof(vs_params_t), + .glsl_uniforms = { + [0] = { .glsl_name = "disp_size", .type = SG_UNIFORMTYPE_FLOAT2} + } }, - .fs = { - .images[0] = { .used = true }, - .samplers[0] = { .used = true }, - .image_sampler_pairs[0] = { .used = true, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, - .source = - "precision mediump float;" - "uniform sampler2D tex;\n" - "varying vec2 uv;\n" - "varying vec4 color;\n" - "void main() {\n" - " gl_FragColor = texture2D(tex, uv) * color;\n" - "}\n" - } + .images[0].stage = SG_SHADERSTAGE_FRAGMENT, + .samplers[0].stage = SG_SHADERSTAGE_FRAGMENT, + .image_sampler_pairs[0] = { .stage = SG_SHADERSTAGE_FRAGMENT, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, }); // pipeline object for imgui rendering @@ -316,7 +316,7 @@ void draw_imgui(ImDrawData* draw_data) { vs_params.disp_size.x = ImGui::GetIO().DisplaySize.x; vs_params.disp_size.y = ImGui::GetIO().DisplaySize.y; sg_apply_pipeline(pip); - sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, SG_RANGE(vs_params)); + sg_apply_uniforms(0, SG_RANGE(vs_params)); for (int cl_index = 0; cl_index < draw_data->CmdListsCount; cl_index++) { const ImDrawList* cl = draw_data->CmdLists[cl_index]; diff --git a/html5/inject-emsc.c b/html5/inject-emsc.c index 7c385c2a..45ac5b48 100644 --- a/html5/inject-emsc.c +++ b/html5/inject-emsc.c @@ -129,7 +129,7 @@ int main() { glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, IMG_WIDTH, IMG_HEIGHT, 0, GL_RGBA, GL_UNSIGNED_BYTE, 0); } sg_reset_state_cache(); - state.bind.fs.images[0] = sg_make_image(&img_desc); + state.bind.images[0] = sg_make_image(&img_desc); // create a GL sampler object sg_sampler_desc smp_desc = { @@ -144,43 +144,43 @@ int main() { glSamplerParameteri(smp_desc.gl_sampler, GL_TEXTURE_WRAP_S, GL_REPEAT); glSamplerParameteri(smp_desc.gl_sampler, GL_TEXTURE_WRAP_T, GL_REPEAT); sg_reset_state_cache(); - state.bind.fs.samplers[0] = sg_make_sampler(&smp_desc); + state.bind.samplers[0] = sg_make_sampler(&smp_desc); // create shader sg_shader shd = sg_make_shader(&(sg_shader_desc){ + .vertex_func.source = + "#version 300 es\n" + "uniform mat4 mvp;\n" + "in vec4 position;\n" + "in vec2 texcoord0;\n" + "out vec2 uv;" + "void main() {\n" + " gl_Position = mvp * position;\n" + " uv = texcoord0;\n" + "}\n", + .fragment_func.source = + "#version 300 es\n" + "precision mediump float;\n" + "uniform sampler2D tex;\n" + "in vec2 uv;\n" + "out vec4 frag_color;\n" + "void main() {\n" + " frag_color = texture(tex, uv);\n" + "}\n", .attrs = { - [0].name = "position", - [1].name = "texcoord0" + [0].glsl_name = "position", + [1].glsl_name = "texcoord0" }, - .vs = { - .uniform_blocks[0] = { - .size = sizeof(vs_params_t), - .uniforms = { - [0] = { .name="mvp", .type=SG_UNIFORMTYPE_MAT4 } - }, + .uniform_blocks[0] = { + .stage = SG_SHADERSTAGE_VERTEX, + .size = sizeof(vs_params_t), + .glsl_uniforms = { + [0] = { .glsl_name="mvp", .type=SG_UNIFORMTYPE_MAT4 } }, - .source = - "uniform mat4 mvp;\n" - "attribute vec4 position;\n" - "attribute vec2 texcoord0;\n" - "varying vec2 uv;" - "void main() {\n" - " gl_Position = mvp * position;\n" - " uv = texcoord0;\n" - "}\n", - }, - .fs = { - .images[0].used = true, - .samplers[0].used = true, - .image_sampler_pairs[0] = { .used = true, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, - .source = - "precision mediump float;\n" - "uniform sampler2D tex;\n" - "varying vec2 uv;\n" - "void main() {\n" - " gl_FragColor = texture2D(tex, uv);\n" - "}\n" }, + .images[0].stage = SG_SHADERSTAGE_FRAGMENT, + .samplers[0].stage = SG_SHADERSTAGE_FRAGMENT, + .image_sampler_pairs[0] = { .stage = SG_SHADERSTAGE_FRAGMENT, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, }); // create pipeline object @@ -230,13 +230,13 @@ static EM_BOOL draw(double time, void* userdata) { } } state.counter++; - sg_update_image(state.bind.fs.images[0], &(sg_image_data){ .subimage[0][0] = SG_RANGE(pixels) }); + sg_update_image(state.bind.images[0], &(sg_image_data){ .subimage[0][0] = SG_RANGE(pixels) }); // ...and draw sg_begin_pass(&(sg_pass){ .action = state.pass_action, .swapchain = emsc_swapchain() }); sg_apply_pipeline(state.pip); sg_apply_bindings(&state.bind); - sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, &SG_RANGE(vs_params)); + sg_apply_uniforms(0, &SG_RANGE(vs_params)); sg_draw(0, 36, 1); sg_end_pass(); sg_commit(); diff --git a/html5/instancing-emsc.c b/html5/instancing-emsc.c index fb479499..84ae9b04 100644 --- a/html5/instancing-emsc.c +++ b/html5/instancing-emsc.c @@ -88,34 +88,38 @@ int main() { // create a shader sg_shader shd = sg_make_shader(&(sg_shader_desc){ - .attrs = { - [0].name = "position", - [1].name = "color0", - [2].name = "instance_pos" - }, - .vs.uniform_blocks[0] = { - .size = sizeof(vs_params_t), - .uniforms = { - [0] = { .name="mvp", .type=SG_UNIFORMTYPE_MAT4 } - } - }, - .vs.source = + .vertex_func.source = + "#version 300 es\n" "uniform mat4 mvp;\n" - "attribute vec3 position;\n" - "attribute vec4 color0;\n" - "attribute vec3 instance_pos;\n" - "varying vec4 color;\n" + "in vec3 position;\n" + "in vec4 color0;\n" + "in vec3 instance_pos;\n" + "out vec4 color;\n" "void main() {\n" " vec4 pos = vec4(position + instance_pos, 1.0);" " gl_Position = mvp * pos;\n" " color = color0;\n" "}\n", - .fs.source = + .fragment_func.source = + "#version 300 es\n" "precision mediump float;\n" - "varying vec4 color;\n" + "in vec4 color;\n" + "out vec4 frag_color;\n" "void main() {\n" - " gl_FragColor = color;\n" - "}\n" + " frag_color = color;\n" + "}\n", + .attrs = { + [0].glsl_name = "position", + [1].glsl_name = "color0", + [2].glsl_name = "instance_pos" + }, + .uniform_blocks[0] = { + .stage = SG_SHADERSTAGE_VERTEX, + .size = sizeof(vs_params_t), + .glsl_uniforms = { + [0] = { .glsl_name="mvp", .type=SG_UNIFORMTYPE_MAT4 } + } + }, }); // pipeline state object, note the vertex attribute definition @@ -192,7 +196,7 @@ static EM_BOOL draw(double time, void* userdata) { sg_begin_pass(&(sg_pass){ .action = state.pass_action, .swapchain = emsc_swapchain() }); sg_apply_pipeline(state.pip); sg_apply_bindings(&state.bind); - sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, &SG_RANGE(vs_params)); + sg_apply_uniforms(0, &SG_RANGE(vs_params)); sg_draw(0, 24, state.cur_num_particles); sg_end_pass(); sg_commit(); diff --git a/html5/mipmap-emsc.c b/html5/mipmap-emsc.c index be05d1e4..f10ce486 100644 --- a/html5/mipmap-emsc.c +++ b/html5/mipmap-emsc.c @@ -90,7 +90,7 @@ int main() { } // create a single image and 12 samplers - state.bind.fs.images[0] = sg_make_image(&(sg_image_desc){ + state.bind.images[0] = sg_make_image(&(sg_image_desc){ .width = 256, .height = 256, .num_mipmaps = 9, @@ -142,39 +142,39 @@ int main() { // shader sg_shader shd = sg_make_shader(&(sg_shader_desc){ + .vertex_func.source = + "#version 300 es\n" + "uniform mat4 mvp;\n" + "in vec4 position;\n" + "in vec2 texcoord0;\n" + "out vec2 uv;\n" + "void main() {\n" + " gl_Position = mvp * position;\n" + " uv = texcoord0;\n" + "}\n", + .fragment_func.source = + "#version 300 es\n" + "precision mediump float;" + "uniform sampler2D tex;" + "in vec2 uv;\n" + "out vec4 frag_color;\n" + "void main() {\n" + " frag_color = texture(tex, uv);\n" + "}\n", .attrs = { - [0].name = "position", - [1].name = "texcoord0" + [0].glsl_name = "position", + [1].glsl_name = "texcoord0" }, - .vs = { - .uniform_blocks[0] = { - .size = sizeof(vs_params_t), - .uniforms = { - [0] = { .name="mvp", .type=SG_UNIFORMTYPE_MAT4 } - } - }, - .source = - "uniform mat4 mvp;\n" - "attribute vec4 position;\n" - "attribute vec2 texcoord0;\n" - "varying vec2 uv;\n" - "void main() {\n" - " gl_Position = mvp * position;\n" - " uv = texcoord0;\n" - "}\n" + .uniform_blocks[0] = { + .stage = SG_SHADERSTAGE_VERTEX, + .size = sizeof(vs_params_t), + .glsl_uniforms = { + [0] = { .glsl_name = "mvp", .type = SG_UNIFORMTYPE_MAT4 } + } }, - .fs = { - .images[0].used = true, - .samplers[0].used = true, - .image_sampler_pairs[0] = { .used = true, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, - .source = - "precision mediump float;" - "uniform sampler2D tex;" - "varying vec2 uv;\n" - "void main() {\n" - " gl_FragColor = texture2D(tex, uv);\n" - "}\n" - } + .images[0].stage = SG_SHADERSTAGE_FRAGMENT, + .samplers[0].stage = SG_SHADERSTAGE_FRAGMENT, + .image_sampler_pairs[0] = { .stage = SG_SHADERSTAGE_FRAGMENT, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, }); // pipeline state @@ -214,9 +214,9 @@ static EM_BOOL draw(double time, void* userdata) { hmm_mat4 model = HMM_MultiplyMat4(HMM_Translate(HMM_Vec3(x, y, 0.0f)), rm); vs_params.mvp = HMM_MultiplyMat4(view_proj, model); - state.bind.fs.samplers[0] = state.smp[i]; + state.bind.samplers[0] = state.smp[i]; sg_apply_bindings(&state.bind); - sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, &SG_RANGE(vs_params)); + sg_apply_uniforms(0, &SG_RANGE(vs_params)); sg_draw(0, 4, 1); } sg_end_pass(); diff --git a/html5/mrt-emsc.c b/html5/mrt-emsc.c index 74102c3d..1c9b4dc0 100644 --- a/html5/mrt-emsc.c +++ b/html5/mrt-emsc.c @@ -175,17 +175,7 @@ int main() { // a shader to render the cube into offscreen MRT render targets sg_shader offscreen_shd = sg_make_shader(&(sg_shader_desc){ - .attrs = { - [0].name = "position", - [1].name = "bright0" - }, - .vs.uniform_blocks[0] = { - .size = sizeof(offscreen_params_t), - .uniforms = { - [0] = { .name="mvp", .type=SG_UNIFORMTYPE_MAT4 } - } - }, - .vs.source = + .vertex_func.source = "#version 300 es\n" "uniform mat4 mvp;\n" "in vec4 position;\n" @@ -195,7 +185,7 @@ int main() { " gl_Position = mvp * position;\n" " bright = bright0;\n" "}\n", - .fs.source = + .fragment_func.source = "#version 300 es\n" "precision mediump float;\n" "in float bright;\n" @@ -206,7 +196,18 @@ int main() { " frag_color_0 = vec4(bright, 0.0, 0.0, 1.0);\n" " frag_color_1 = vec4(0.0, bright, 0.0, 1.0);\n" " frag_color_2 = vec4(0.0, 0.0, bright, 1.0);\n" - "}\n" + "}\n", + .attrs = { + [0].glsl_name = "position", + [1].glsl_name = "bright0" + }, + .uniform_blocks[0] = { + .stage = SG_SHADERSTAGE_VERTEX, + .size = sizeof(offscreen_params_t), + .glsl_uniforms = { + [0] = { .glsl_name = "mvp", .type = SG_UNIFORMTYPE_MAT4 } + } + }, }); // pipeline object for the offscreen-rendered cube @@ -247,70 +248,65 @@ int main() { // resource bindings to render the fullscreen quad state.display.fsq_bind = (sg_bindings){ .vertex_buffers[0] = quad_buf, - .fs = { - .images = { - [0] = state.offscreen.attachments_desc.resolves[0].image, - [1] = state.offscreen.attachments_desc.resolves[1].image, - [2] = state.offscreen.attachments_desc.resolves[2].image, - }, - .samplers[0] = smp, - } + .images = { + [0] = state.offscreen.attachments_desc.resolves[0].image, + [1] = state.offscreen.attachments_desc.resolves[1].image, + [2] = state.offscreen.attachments_desc.resolves[2].image, + }, + .samplers[0] = smp, }; // a shader to render a fullscreen rectangle, which 'composes' // the 3 offscreen render target images onto the screen sg_shader fsq_shd = sg_make_shader(&(sg_shader_desc){ - .attrs[0].name = "pos", - .vs = { - .uniform_blocks[0] = { - .size = sizeof(params_t), - .uniforms = { - [0] = { .name="offset", .type=SG_UNIFORMTYPE_FLOAT2} - } - }, - .source = - "#version 300 es\n" - "uniform vec2 offset;" - "in vec2 pos;\n" - "out vec2 uv0;\n" - "out vec2 uv1;\n" - "out vec2 uv2;\n" - "void main() {\n" - " gl_Position = vec4(pos*2.0-1.0, 0.5, 1.0);\n" - " uv0 = pos + vec2(offset.x, 0.0);\n" - " uv1 = pos + vec2(0.0, offset.y);\n" - " uv2 = pos;\n" - "}\n", + .vertex_func.source = + "#version 300 es\n" + "uniform vec2 offset;" + "in vec2 pos;\n" + "out vec2 uv0;\n" + "out vec2 uv1;\n" + "out vec2 uv2;\n" + "void main() {\n" + " gl_Position = vec4(pos*2.0-1.0, 0.5, 1.0);\n" + " uv0 = pos + vec2(offset.x, 0.0);\n" + " uv1 = pos + vec2(0.0, offset.y);\n" + " uv2 = pos;\n" + "}\n", + .fragment_func.source = + "#version 300 es\n" + "precision mediump float;\n" + "uniform sampler2D tex0;\n" + "uniform sampler2D tex1;\n" + "uniform sampler2D tex2;\n" + "in vec2 uv0;\n" + "in vec2 uv1;\n" + "in vec2 uv2;\n" + "out vec4 frag_color;\n" + "void main() {\n" + " vec3 c0 = texture(tex0, uv0).xyz;\n" + " vec3 c1 = texture(tex1, uv1).xyz;\n" + " vec3 c2 = texture(tex2, uv2).xyz;\n" + " frag_color = vec4(c0 + c1 + c2, 1.0);\n" + "}\n", + .attrs[0].glsl_name = "pos", + .uniform_blocks[0] = { + .stage = SG_SHADERSTAGE_VERTEX, + .size = sizeof(params_t), + .glsl_uniforms = { + [0] = { .glsl_name = "offset", .type = SG_UNIFORMTYPE_FLOAT2} + } + }, + .images = { + [0].stage = SG_SHADERSTAGE_FRAGMENT, + [1].stage = SG_SHADERSTAGE_FRAGMENT, + [2].stage = SG_SHADERSTAGE_FRAGMENT, + }, + .samplers[0].stage = SG_SHADERSTAGE_FRAGMENT, + .image_sampler_pairs = { + [0] = { .stage = SG_SHADERSTAGE_FRAGMENT, .glsl_name = "tex0", .image_slot = 0, .sampler_slot = 0 }, + [1] = { .stage = SG_SHADERSTAGE_FRAGMENT, .glsl_name = "tex1", .image_slot = 1, .sampler_slot = 0 }, + [2] = { .stage = SG_SHADERSTAGE_FRAGMENT, .glsl_name = "tex2", .image_slot = 2, .sampler_slot = 0 }, }, - .fs = { - .images = { - [0].used = true, - [1].used = true, - [2].used = true, - }, - .samplers[0].used = true, - .image_sampler_pairs = { - [0] = { .used = true, .glsl_name = "tex0", .image_slot = 0, .sampler_slot = 0 }, - [1] = { .used = true, .glsl_name = "tex1", .image_slot = 1, .sampler_slot = 0 }, - [2] = { .used = true, .glsl_name = "tex2", .image_slot = 2, .sampler_slot = 0 }, - }, - .source = - "#version 300 es\n" - "precision mediump float;\n" - "uniform sampler2D tex0;\n" - "uniform sampler2D tex1;\n" - "uniform sampler2D tex2;\n" - "in vec2 uv0;\n" - "in vec2 uv1;\n" - "in vec2 uv2;\n" - "out vec4 frag_color;\n" - "void main() {\n" - " vec3 c0 = texture(tex0, uv0).xyz;\n" - " vec3 c1 = texture(tex1, uv1).xyz;\n" - " vec3 c2 = texture(tex2, uv2).xyz;\n" - " frag_color = vec4(c0 + c1 + c2, 1.0);\n" - "}\n" - } }); // the pipeline object for the fullscreen rectangle @@ -328,37 +324,32 @@ int main() { }, .primitive_type = SG_PRIMITIVETYPE_TRIANGLE_STRIP, .shader = sg_make_shader(&(sg_shader_desc){ - .attrs[0].name = "pos", - .vs = { - .source = - "#version 300 es\n" - "uniform vec2 offset;" - "in vec2 pos;\n" - "out vec2 uv;\n" - "void main() {\n" - " gl_Position = vec4(pos*2.0-1.0, 0.5, 1.0);\n" - " uv = pos;\n" - "}\n", - }, - .fs = { - .images[0].used = true, - .samplers[0].used = true, - .image_sampler_pairs[0] = { .used = true, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, - .source = - "#version 300 es\n" - "precision mediump float;\n" - "uniform sampler2D tex;\n" - "in vec2 uv;\n" - "out vec4 frag_color;\n" - "void main() {\n" - " frag_color = vec4(texture(tex,uv).xyz, 1.0);\n" - "}\n" - }, + .vertex_func.source = + "#version 300 es\n" + "in vec2 pos;\n" + "out vec2 uv;\n" + "void main() {\n" + " gl_Position = vec4(pos*2.0-1.0, 0.5, 1.0);\n" + " uv = pos;\n" + "}\n", + .fragment_func.source = + "#version 300 es\n" + "precision mediump float;\n" + "uniform sampler2D tex;\n" + "in vec2 uv;\n" + "out vec4 frag_color;\n" + "void main() {\n" + " frag_color = vec4(texture(tex,uv).xyz, 1.0);\n" + "}\n", + .attrs[0].glsl_name = "pos", + .images[0].stage = SG_SHADERSTAGE_FRAGMENT, + .samplers[0].stage = SG_SHADERSTAGE_FRAGMENT, + .image_sampler_pairs[0] = { .stage = SG_SHADERSTAGE_FRAGMENT, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, }) }); state.display.dbg_bind = (sg_bindings) { .vertex_buffers[0] = quad_buf, - .fs.samplers[0] = smp, + .samplers[0] = smp, // images will be filled right before rendering }; @@ -398,7 +389,7 @@ static EM_BOOL draw(double time, void* userdata) { }); sg_apply_pipeline(state.offscreen.pip); sg_apply_bindings(&state.offscreen.bind); - sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, &SG_RANGE(offscreen_params)); + sg_apply_uniforms(0, &SG_RANGE(offscreen_params)); sg_draw(0, 36, 1); sg_end_pass(); @@ -410,12 +401,12 @@ static EM_BOOL draw(double time, void* userdata) { }); sg_apply_pipeline(state.display.fsq_pip); sg_apply_bindings(&state.display.fsq_bind); - sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, &SG_RANGE(params)); + sg_apply_uniforms(0, &SG_RANGE(params)); sg_draw(0, 4, 1); sg_apply_pipeline(state.display.dbg_pip); for (int i = 0; i < 3; i++) { sg_apply_viewport(i*100, 0, 100, 100, false); - state.display.dbg_bind.fs.images[0] = state.offscreen.attachments_desc.resolves[i].image; + state.display.dbg_bind.images[0] = state.offscreen.attachments_desc.resolves[i].image; sg_apply_bindings(&state.display.dbg_bind); sg_draw(0, 4, 1); } diff --git a/html5/noninterleaved-emsc.c b/html5/noninterleaved-emsc.c index 125fbea4..d320a233 100644 --- a/html5/noninterleaved-emsc.c +++ b/html5/noninterleaved-emsc.c @@ -79,31 +79,35 @@ int main() { // create shader sg_shader shd = sg_make_shader(&(sg_shader_desc){ - .attrs = { - [0].name = "position", - [1].name = "color0" - }, - .vs.uniform_blocks[0] = { - .size = sizeof(params_t), - .uniforms = { - [0] = { .name="mvp", .type=SG_UNIFORMTYPE_MAT4 } - } - }, - .vs.source = + .vertex_func.source = + "#version 300 es\n" "uniform mat4 mvp;\n" - "attribute vec4 position;\n" - "attribute vec4 color0;\n" - "varying vec4 color;\n" + "in vec4 position;\n" + "in vec4 color0;\n" + "out vec4 color;\n" "void main() {\n" " gl_Position = mvp * position;\n" " color = color0;\n" "}\n", - .fs.source = + .fragment_func.source = + "#version 300 es\n" "precision mediump float;\n" - "varying vec4 color;\n" + "in vec4 color;\n" + "out vec4 frag_color;\n" "void main() {\n" - " gl_FragColor = color;\n" - "}\n" + " frag_color = color;\n" + "}\n", + .attrs = { + [0].glsl_name = "position", + [1].glsl_name = "color0" + }, + .uniform_blocks[0] = { + .stage = SG_SHADERSTAGE_VERTEX, + .size = sizeof(params_t), + .glsl_uniforms = { + [0] = { .glsl_name = "mvp", .type = SG_UNIFORMTYPE_MAT4 } + } + }, }); // create pipeline object @@ -168,7 +172,7 @@ static EM_BOOL draw(double time, void* userdata) { sg_begin_pass(&(sg_pass){ .action = state.pass_action, .swapchain = emsc_swapchain() }); sg_apply_pipeline(state.pip); sg_apply_bindings(&state.bind); - sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, &SG_RANGE(vs_params)); + sg_apply_uniforms(0, &SG_RANGE(vs_params)); sg_draw(0, 36, 1); sg_end_pass(); sg_commit(); diff --git a/html5/offscreen-emsc.c b/html5/offscreen-emsc.c index 9394bdaf..0c3eb124 100644 --- a/html5/offscreen-emsc.c +++ b/html5/offscreen-emsc.c @@ -127,17 +127,7 @@ int main() { // shader for the non-textured cube, rendered in the offscreen pass sg_shader offscreen_shd = sg_make_shader(&(sg_shader_desc) { - .attrs = { - [0].name = "position", - [1].name = "color0" - }, - .vs.uniform_blocks[0] = { - .size = sizeof(params_t), - .uniforms = { - [0] = { .name="mvp", .type=SG_UNIFORMTYPE_MAT4 } - } - }, - .vs.source = + .vertex_func.source = "uniform mat4 mvp;\n" "attribute vec4 position;\n" "attribute vec4 color0;\n" @@ -146,54 +136,100 @@ int main() { " gl_Position = mvp * position;\n" " color = color0;\n" "}\n", - .fs.source = + // FIXME: switching to WebGL2 shader causes all sorts of weird errors + //"#version 300 es\n", + //"uniform mat4 mvp;\n" + //"in vec4 position;\n" + //"in vec4 color0;\n" + //"out vec4 color;\n" + //"void main() {\n" + //" gl_Position = mvp * position;\n" + //" color = color0;\n" + //"}\n", + .fragment_func.source = "precision mediump float;\n" "varying vec4 color;\n" "void main() {\n" " gl_FragColor = color;\n" - "}\n" + "}\n", + //"#version 300 es\n" + //"precision mediump float;\n" + //"in vec4 color;\n" + //"out vec4 frag_color;\n" + //"void main() {\n" + //" frag_color = color;\n" + //"}\n", + .attrs = { + [0].glsl_name = "position", + [1].glsl_name = "color0" + }, + .uniform_blocks[0] = { + .stage = SG_SHADERSTAGE_VERTEX, + .size = sizeof(params_t), + .glsl_uniforms = { + [0] = { .glsl_name = "mvp", .type = SG_UNIFORMTYPE_MAT4 } + } + }, }); // ...and a second shader for rendering a textured cube in the default pass sg_shader default_shd = sg_make_shader(&(sg_shader_desc){ + .vertex_func.source = + //"uniform mat4 mvp;\n" + //"attribute vec4 position;\n" + //"attribute vec4 color0;\n" + //"attribute vec2 texcoord0;\n" + //"varying vec4 color;\n" + //"varying vec2 uv;\n" + //"void main() {\n" + //" gl_Position = mvp * position;\n" + //" color = color0;\n" + //" uv = texcoord0;\n" + //"}\n", + "#version 300 es\n" + "uniform mat4 mvp;\n" + "in vec4 position;\n" + "in vec4 color0;\n" + "in vec2 texcoord0;\n" + "out vec4 color;\n" + "out vec2 uv;\n" + "void main() {\n" + " gl_Position = mvp * position;\n" + " color = color0;\n" + " uv = texcoord0;\n" + "}\n", + .fragment_func.source = + //"precision mediump float;" + //"uniform sampler2D tex;\n" + //"varying vec4 color;\n" + //"varying vec2 uv;\n" + //"void main() {\n" + //" gl_FragColor = texture2D(tex, uv) + color * 0.5;\n" + //"}\n", + "#version 300 es\n" + "precision mediump float;" + "uniform sampler2D tex;\n" + "in vec4 color;\n" + "in vec2 uv;\n" + "out vec4 frag_color;\n" + "void main() {\n" + " frag_color = texture(tex, uv) + color * 0.5;\n" + "}\n", .attrs = { - [0].name = "position", - [1].name = "color0", - [2].name = "texcoord0" + [0].glsl_name = "position", + [1].glsl_name = "color0", + [2].glsl_name = "texcoord0" }, - .vs = { - .uniform_blocks[0] = { - .size = sizeof(params_t), - .uniforms = { - [0] = { .name="mvp", .type=SG_UNIFORMTYPE_MAT4 } - } - }, - .source = - "uniform mat4 mvp;\n" - "attribute vec4 position;\n" - "attribute vec4 color0;\n" - "attribute vec2 texcoord0;\n" - "varying vec4 color;\n" - "varying vec2 uv;\n" - "void main() {\n" - " gl_Position = mvp * position;\n" - " color = color0;\n" - " uv = texcoord0;\n" - "}\n", + .uniform_blocks[0] = { + .stage = SG_SHADERSTAGE_VERTEX, + .size = sizeof(params_t), + .glsl_uniforms = { + [0] = { .glsl_name = "mvp", .type = SG_UNIFORMTYPE_MAT4 } + } }, - .fs = { - .images[0].used = true, - .samplers[0].used = true, - .image_sampler_pairs[0] = { .used = true, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, - .source = - "precision mediump float;" - "uniform sampler2D tex;\n" - "varying vec4 color;\n" - "varying vec2 uv;\n" - "void main() {\n" - " gl_FragColor = texture2D(tex, uv) + color * 0.5;\n" - "}\n" - } + .images[0].stage = SG_SHADERSTAGE_FRAGMENT, + .samplers[0].stage = SG_SHADERSTAGE_FRAGMENT, + .image_sampler_pairs[0] = { .stage = SG_SHADERSTAGE_FRAGMENT, .glsl_name = "tex", .image_slot = 0, .sampler_slot = 0 }, }); // pipeline object for offscreen rendering, don't need texcoords here @@ -248,10 +284,8 @@ int main() { state.display.bind = (sg_bindings){ .vertex_buffers[0] = vbuf, .index_buffer = ibuf, - .fs = { - .images[0] = color_img, - .samplers[0] = smp, - } + .images[0] = color_img, + .samplers[0] = smp, }; // hand off control to browser loop @@ -282,7 +316,7 @@ static EM_BOOL draw(double time, void* userdata) { }); sg_apply_pipeline(state.offscreen.pip); sg_apply_bindings(&state.offscreen.bind); - sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, &SG_RANGE(vs_params)); + sg_apply_uniforms(0, &SG_RANGE(vs_params)); sg_draw(0, 36, 1); sg_end_pass(); @@ -294,7 +328,7 @@ static EM_BOOL draw(double time, void* userdata) { }); sg_apply_pipeline(state.display.pip); sg_apply_bindings(&state.display.bind); - sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, &SG_RANGE(vs_params)); + sg_apply_uniforms(0, &SG_RANGE(vs_params)); sg_draw(0, 36, 1); sg_end_pass(); sg_commit();