diff --git a/source/engine/3d/model.c b/source/engine/3d/model.c index 5623dce..03dd84e 100644 --- a/source/engine/3d/model.c +++ b/source/engine/3d/model.c @@ -75,9 +75,9 @@ void model_init() { .attrs = { [0].format = SG_VERTEXFORMAT_FLOAT3, [0].buffer_index = 0, /* position */ - [1].format = SG_VERTEXFORMAT_FLOAT2, + [1].format = SG_VERTEXFORMAT_USHORT2N, [1].buffer_index = 1, /* tex coords */ - [2].format = SG_VERTEXFORMAT_FLOAT3, + [2].format = SG_VERTEXFORMAT_UINT10_N2, [2].buffer_index = 2, /* normal */ }, }, @@ -107,6 +107,24 @@ cgltf_attribute *get_attr_type(cgltf_primitive p, cgltf_attribute_type t) return NULL; } +unsigned short pack_short_texcoord(float c) +{ + return c * USHRT_MAX; +} + +uint32_t pack_int10_n2(float *norm) +{ + uint32_t ni[3]; + + for (int i = 0; i < 3; i++) { + ni[i] = fabs(norm[i]) * 511.0 + 0.5; + ni[i] = (ni[i] > 511) ? 511 : ni[i]; + ni[i] = ( norm[i] < 0.0 ) ? -ni[i] : ni[i]; + } + + return (ni[0] & 0x3FF) | ( (ni[1] & 0x3FF) << 10) | ( (ni[2] & 0x3FF) << 20) | ( (0 & 0x3) << 30); +} + struct model *MakeModel(const char *path) { YughWarn("Making the model from %s.", path); cgltf_options options = {0}; @@ -189,6 +207,9 @@ struct model *MakeModel(const char *path) { cgltf_accessor_unpack_floats(attribute.data, vs, n); + uint32_t *packed_norms; + unsigned short *packed_coords; + switch (attribute.type) { case cgltf_attribute_type_position: model->meshes[j].bind.vertex_buffers[0] = sg_make_buffer(&(sg_buffer_desc){ @@ -198,25 +219,37 @@ struct model *MakeModel(const char *path) { case cgltf_attribute_type_normal: has_norm = 1; + packed_norms = malloc(model->meshes[j].face_count * sizeof(uint32_t));; + for (int i = 0; i < model->meshes[j].face_count; i++) + packed_norms[i] = pack_int10_n2(vs + i*3); + model->meshes[j].bind.vertex_buffers[2] = sg_make_buffer(&(sg_buffer_desc){ - .data.ptr = vs, - .data.size = sizeof(float) * n}); + .data.ptr = packed_norms, + .data.size = sizeof(uint32_t) * model->meshes[j].face_count}); + + free (packed_norms); break; case cgltf_attribute_type_tangent: break; case cgltf_attribute_type_texcoord: + packed_coords = malloc(model->meshes[j].face_count * 2 * sizeof(unsigned short)); + for (int i = 0; i < model->meshes[j].face_count*2; i++) + packed_coords[i] = pack_short_texcoord(vs[i]); + model->meshes[j].bind.vertex_buffers[1] = sg_make_buffer(&(sg_buffer_desc){ .data.ptr = vs, - .data.size = sizeof(float) * n}); + .data.size = sizeof(unsigned short) * 2 * model->meshes[j].face_count}); + + free(packed_coords); break; } } if (!has_norm) { YughWarn("Model does not have normals. Generating them."); - float norms[3 * model->meshes[j].face_count]; + uint32_t norms[model->meshes[j].face_count]; cgltf_attribute *pa = get_attr_type(primitive, cgltf_attribute_type_position); @@ -224,24 +257,23 @@ struct model *MakeModel(const char *path) { float ps[n]; cgltf_accessor_unpack_floats(pa->data,ps,n); - for (int i = 0; i < model->meshes[j].face_count/3; i++) { - int o = i*9; + for (int i = 0, face=0; i < model->meshes[j].face_count/3; i++, face+=9) { + int o = face; HMM_Vec3 a = {ps[o], ps[o+1],ps[o+2]}; o += 3; HMM_Vec3 b = {ps[o], ps[o+1],ps[o+2]}; o += 3; HMM_Vec3 c = {ps[o], ps[o+1],ps[o+2]}; HMM_Vec3 norm = HMM_NormV3(HMM_Cross(HMM_SubV3(b,a), HMM_SubV3(c,a))); - for (int j = 0; j < 3; j++) { - norms[i*9+j*3+0] = norm.X; - norms[i*9+j*3+1] = norm.Y; - norms[i*9+j*3+2] = norm.Z; - } + + uint32_t packed_norm = pack_int10_n2(norm.Elements); + for (int j = 0; j < 3; j++) + norms[i*3+j] = packed_norm; } model->meshes[j].bind.vertex_buffers[2] = sg_make_buffer(&(sg_buffer_desc){ .data.ptr = norms, - .data.size = sizeof(float) * model->meshes[j].face_count * 3 + .data.size = sizeof(uint32_t) * model->meshes[j].face_count }); } } diff --git a/source/engine/datastream.c b/source/engine/datastream.c index 8e3516f..335b321 100644 --- a/source/engine/datastream.c +++ b/source/engine/datastream.c @@ -14,24 +14,26 @@ #include #include -struct shader *vid_shader; +#include "sokol/sokol_gfx.h" + +sg_shader vid_shader; +sg_pipeline vid_pipeline; +sg_bindings vid_bind; + -static void ds_update_texture(uint32_t unit, uint32_t texture, plm_plane_t *plane) { - /* - glActiveTexture(unit); - glBindTexture(GL_TEXTURE_2D, texture); - glTexImage2D(GL_TEXTURE_2D, 0, GL_RED, plane->width, plane->height, 0, GL_RED, GL_UNSIGNED_BYTE, plane->data); - */ -} static void render_frame(plm_t *mpeg, plm_frame_t *frame, void *user) { struct datastream *ds = user; - shader_use(ds->shader); - /* - ds_update_texture(GL_TEXTURE0, ds->texture_y, &frame->y); - ds_update_texture(GL_TEXTURE1, ds->texture_cb, &frame->cb); - ds_update_texture(GL_TEXTURE2, ds->texture_cr, &frame->cr); - */ + uint8_t rgb[frame->height*frame->width*4]; + plm_frame_to_rgba(frame, rgb, frame->width*4); + sg_image_data imgd; + sg_range ir = { + .ptr = rgb, + .size = frame->height*frame->width*4*sizeof(uint8_t) + }; + + imgd.subimage[0][0] = ir; + sg_update_image(ds->img, &imgd); } static void render_audio(plm_t *mpeg, plm_samples_t *samples, void *user) { @@ -44,16 +46,6 @@ static void render_audio(plm_t *mpeg, plm_samples_t *samples, void *user) { } } -struct Texture *ds_maketexture(struct datastream *ds) { - /* - struct Texture *new = malloc(sizeof(*new)); - new->id = ds->texture_cb; - new->width = 500; - new->height = 500; - return new; - */ -} - void ds_openvideo(struct datastream *ds, const char *video, const char *adriver) { // ds_stop(ds); char buf[MAXPATH] = {'\0'}; @@ -64,6 +56,11 @@ void ds_openvideo(struct datastream *ds, const char *video, const char *adriver) YughLog(0, 0, "Couldn't open %s", video); } + ds->img = sg_make_image(&(sg_image_desc){ + .width = plm_get_width(ds->plm), + .height = plm_get_height(ds->plm) + }); + YughLog(0, 0, "Opened %s - framerate: %f, samplerate: %d, audio streams: %i, duration: %f", video, plm_get_framerate(ds->plm), @@ -107,37 +104,14 @@ void ds_openvideo(struct datastream *ds, const char *video, const char *adriver) } struct datastream *MakeDatastream() { - struct datastream *newds = malloc(sizeof(*newds)); - /* - if (!vid_shader) vid_shader = MakeShader("videovert.glsl", "videofrag.glsl"); - - newds->shader = vid_shader; - shader_use(newds->shader); - glGenTextures(1, &newds->texture_y); - glBindTexture(GL_TEXTURE_2D, newds->texture_y); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); - shader_setint(newds->shader, "texture_y", 0); - - glGenTextures(1, &newds->texture_cb); - glBindTexture(GL_TEXTURE_2D, newds->texture_cb); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); - shader_setint(newds->shader, "texture_cb", 1); - - glGenTextures(1, &newds->texture_cr); - glBindTexture(GL_TEXTURE_2D, newds->texture_cr); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); - shader_setint(newds->shader, "texture_cr", 2); - */ - return newds; + vid_shader = sg_make_shader(&(sg_shader_desc){ + .vs.source = slurp_text("shaders/videovert.glsl"), + .fs.source = slurp_text("shaders/videofrag.glsl"), + .fs.images[0] = { + .name = "video", + .image_type = SG_IMAGETYPE_2D, + .sampler_type = SG_SAMPLERTYPE_FLOAT + }}); } void ds_advance(struct datastream *ds, double s) { diff --git a/source/engine/datastream.h b/source/engine/datastream.h index 4f297af..9248527 100644 --- a/source/engine/datastream.h +++ b/source/engine/datastream.h @@ -4,24 +4,23 @@ #include #include +#include "sokol/sokol_gfx.h" + struct soundstream; struct datastream { plm_t *plm; - struct shader *shader; double last_time; int playing; int audio_device; - uint32_t texture_y; - uint32_t texture_cb; - uint32_t texture_cr; + sg_image img; + int width; + int height; struct soundstream *astream; }; struct Texture; -extern struct shader *vid_shader; - struct datastream *MakeDatastream(); void ds_openvideo(struct datastream *ds, const char *path, const char *adriver); struct Texture *ds_maketexture(struct datastream *); diff --git a/source/engine/font.c b/source/engine/font.c index 23b801b..9828633 100644 --- a/source/engine/font.c +++ b/source/engine/font.c @@ -215,7 +215,7 @@ void text_flush() { if (curchar == 0) return; sg_apply_pipeline(pipe_text); sg_apply_bindings(&bind_text); - sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, SG_RANGE_REF(projection)); + sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, SG_RANGE_REF(hudproj)); sg_range verts; verts.ptr = text_buffer; diff --git a/source/engine/openglrender.c b/source/engine/openglrender.c index f733cfc..ca12914 100644 --- a/source/engine/openglrender.c +++ b/source/engine/openglrender.c @@ -40,6 +40,7 @@ float gridOpacity = 0.3f; mfloat_t proj[16]; + // Debug render modes bool renderGizmos = false; bool showGrid = true; @@ -233,6 +234,7 @@ float cam_zoom() { return zoom; } void add_zoom(float val) { zoom = val; } mfloat_t projection[16] = {0.f}; +float hudproj[16] = {0.f}; HMM_Vec3 dirl_pos = {4, 100, 20}; @@ -281,8 +283,7 @@ void openglRender(struct window *window) { pos.y - zoom * window->height / 2, pos.y + zoom * window->height / 2, -1.f, 1.f); - mfloat_t ui_projection[16] = {0.f}; - mat4_ortho(ui_projection, 0, window->width, 0, window->height, -1.f, 1.f); + mat4_ortho(hudproj, 0, window->width, 0, window->height, -1.f, 1.f); sprite_draw_all(); sprite_flush(); diff --git a/source/engine/openglrender.h b/source/engine/openglrender.h index fdabb24..6a71828 100644 --- a/source/engine/openglrender.h +++ b/source/engine/openglrender.h @@ -19,6 +19,7 @@ extern int renderMode; extern HMM_Vec3 dirl_pos; extern float projection[16]; +extern float hudproj[16]; extern float gridScale; extern float smallGridUnit; diff --git a/source/engine/sprite.c b/source/engine/sprite.c index b4cd5b8..a23657d 100644 --- a/source/engine/sprite.c +++ b/source/engine/sprite.c @@ -217,15 +217,15 @@ void sprite_setframe(struct sprite *sprite, struct glrect *frame) { } void video_draw(struct datastream *stream, mfloat_t position[2], mfloat_t size[2], float rotate, mfloat_t color[3]) { - shader_use(vid_shader); +// shader_use(vid_shader); static mfloat_t model[16]; memcpy(model, UNITMAT4, sizeof(UNITMAT4)); mat4_translate_vec2(model, position); mat4_scale_vec2(model, size); - shader_setmat4(vid_shader, "model", model); - shader_setvec3(vid_shader, "spriteColor", color); +// shader_setmat4(vid_shader, "model", model); +// shader_setvec3(vid_shader, "spriteColor", color); /* glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, stream->texture_y);