Skip to content

Commit

Permalink
Merge pull request #124 from romainguy/rg/KHR_materials_specular
Browse files Browse the repository at this point in the history
Add support for KHR_materials_specular
  • Loading branch information
jkuhlmann authored Sep 16, 2020
2 parents 062695f + 2bf0b35 commit 468ad38
Show file tree
Hide file tree
Showing 3 changed files with 89 additions and 2 deletions.
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,7 @@ cgltf also supports some glTF extensions:
- KHR_materials_clearcoat
- KHR_materials_ior
- KHR_materials_pbrSpecularGlossiness
- KHR_materials_specular
- KHR_materials_transmission
- KHR_materials_unlit
- KHR_texture_transform
Expand Down
65 changes: 65 additions & 0 deletions cgltf.h
Original file line number Diff line number Diff line change
Expand Up @@ -408,6 +408,13 @@ typedef struct cgltf_ior
cgltf_float ior;
} cgltf_ior;

typedef struct cgltf_specular
{
cgltf_texture_view specular_texture;
cgltf_float specular_color_factor[3];
cgltf_float specular_factor;
} cgltf_specular;

typedef struct cgltf_material
{
char* name;
Expand All @@ -416,10 +423,12 @@ typedef struct cgltf_material
cgltf_bool has_clearcoat;
cgltf_bool has_transmission;
cgltf_bool has_ior;
cgltf_bool has_specular;
cgltf_pbr_metallic_roughness pbr_metallic_roughness;
cgltf_pbr_specular_glossiness pbr_specular_glossiness;
cgltf_clearcoat clearcoat;
cgltf_ior ior;
cgltf_specular specular;
cgltf_transmission transmission;
cgltf_texture_view normal_texture;
cgltf_texture_view occlusion_texture;
Expand Down Expand Up @@ -1661,6 +1670,10 @@ void cgltf_free(cgltf_data* data)
cgltf_free_extensions(data, data->materials[i].clearcoat.clearcoat_roughness_texture.extensions, data->materials[i].clearcoat.clearcoat_roughness_texture.extensions_count);
cgltf_free_extensions(data, data->materials[i].clearcoat.clearcoat_normal_texture.extensions, data->materials[i].clearcoat.clearcoat_normal_texture.extensions_count);
}
if(data->materials[i].has_specular)
{
cgltf_free_extensions(data, data->materials[i].specular.specular_texture.extensions, data->materials[i].specular.specular_texture.extensions_count);
}
if(data->materials[i].has_transmission)
{
cgltf_free_extensions(data, data->materials[i].transmission.transmission_texture.extensions, data->materials[i].transmission.transmission_texture.extensions_count);
Expand Down Expand Up @@ -3288,6 +3301,9 @@ static int cgltf_parse_json_ior(jsmntok_t const* tokens, int i, const uint8_t* j
int size = tokens[i].size;
++i;

// Default values
out_ior->ior = 1.5f;

for (int j = 0; j < size; ++j)
{
CGLTF_CHECK_KEY(tokens[i]);
Expand All @@ -3312,6 +3328,48 @@ static int cgltf_parse_json_ior(jsmntok_t const* tokens, int i, const uint8_t* j
return i;
}

static int cgltf_parse_json_specular(cgltf_options* options, jsmntok_t const* tokens, int i, const uint8_t* json_chunk, cgltf_specular* out_specular)
{
CGLTF_CHECK_TOKTYPE(tokens[i], JSMN_OBJECT);
int size = tokens[i].size;
++i;

// Default values
out_specular->specular_factor = 1.0f;
cgltf_fill_float_array(out_specular->specular_color_factor, 3, 1.0f);

for (int j = 0; j < size; ++j)
{
CGLTF_CHECK_KEY(tokens[i]);

if (cgltf_json_strcmp(tokens+i, json_chunk, "specularFactor") == 0)
{
++i;
out_specular->specular_factor = cgltf_json_to_float(tokens + i, json_chunk);
++i;
}
else if (cgltf_json_strcmp(tokens+i, json_chunk, "specularColorFactor") == 0)
{
i = cgltf_parse_json_float_array(tokens, i + 1, json_chunk, out_specular->specular_color_factor, 3);
}
else if (cgltf_json_strcmp(tokens+i, json_chunk, "specularTexture") == 0)
{
i = cgltf_parse_json_texture_view(options, tokens, i + 1, json_chunk, &out_specular->specular_texture);
}
else
{
i = cgltf_skip_json(tokens, i+1);
}

if (i < 0)
{
return i;
}
}

return i;
}

static int cgltf_parse_json_transmission(cgltf_options* options, jsmntok_t const* tokens, int i, const uint8_t* json_chunk, cgltf_transmission* out_transmission)
{
CGLTF_CHECK_TOKTYPE(tokens[i], JSMN_OBJECT);
Expand Down Expand Up @@ -3638,6 +3696,11 @@ static int cgltf_parse_json_material(cgltf_options* options, jsmntok_t const* to
out_material->has_ior = 1;
i = cgltf_parse_json_ior(tokens, i + 1, json_chunk, &out_material->ior);
}
else if (cgltf_json_strcmp(tokens+i, json_chunk, "KHR_materials_specular") == 0)
{
out_material->has_specular = 1;
i = cgltf_parse_json_specular(options, tokens, i + 1, json_chunk, &out_material->specular);
}
else if (cgltf_json_strcmp(tokens+i, json_chunk, "KHR_materials_transmission") == 0)
{
out_material->has_transmission = 1;
Expand Down Expand Up @@ -5242,6 +5305,8 @@ static int cgltf_fixup_pointers(cgltf_data* data)
CGLTF_PTRFIXUP(data->materials[i].clearcoat.clearcoat_roughness_texture.texture, data->textures, data->textures_count);
CGLTF_PTRFIXUP(data->materials[i].clearcoat.clearcoat_normal_texture.texture, data->textures, data->textures_count);

CGLTF_PTRFIXUP(data->materials[i].specular.specular_texture.texture, data->textures, data->textures_count);

CGLTF_PTRFIXUP(data->materials[i].transmission.transmission_texture.texture, data->textures, data->textures_count);
}

Expand Down
25 changes: 23 additions & 2 deletions cgltf_write.h
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,8 @@ cgltf_size cgltf_write(const cgltf_options* options, char* buffer, cgltf_size si
#define CGLTF_EXTENSION_FLAG_DRACO_MESH_COMPRESSION (1 << 4)
#define CGLTF_EXTENSION_FLAG_MATERIALS_CLEARCOAT (1 << 5)
#define CGLTF_EXTENSION_FLAG_MATERIALS_IOR (1 << 6)
#define CGLTF_EXTENSION_FLAG_MATERIALS_TRANSMISSION (1 << 7)
#define CGLTF_EXTENSION_FLAG_MATERIALS_SPECULAR (1 << 7)
#define CGLTF_EXTENSION_FLAG_MATERIALS_TRANSMISSION (1 << 8)

typedef struct {
char* buffer;
Expand Down Expand Up @@ -514,6 +515,11 @@ static void cgltf_write_material(cgltf_write_context* context, const cgltf_mater
context->extension_flags |= CGLTF_EXTENSION_FLAG_MATERIALS_IOR;
}

if (material->has_specular)
{
context->extension_flags |= CGLTF_EXTENSION_FLAG_MATERIALS_SPECULAR;
}

if (material->has_pbr_metallic_roughness)
{
const cgltf_pbr_metallic_roughness* params = &material->pbr_metallic_roughness;
Expand All @@ -530,7 +536,7 @@ static void cgltf_write_material(cgltf_write_context* context, const cgltf_mater
cgltf_write_line(context, "}");
}

if (material->unlit || material->has_pbr_specular_glossiness || material->has_clearcoat || material->has_ior || material->has_transmission)
if (material->unlit || material->has_pbr_specular_glossiness || material->has_clearcoat || material->has_ior || material->has_specular || material->has_transmission)
{
cgltf_write_line(context, "\"extensions\": {");
if (material->has_clearcoat)
Expand All @@ -551,6 +557,18 @@ static void cgltf_write_material(cgltf_write_context* context, const cgltf_mater
cgltf_write_floatprop(context, "ior", params->ior, 1.5f);
cgltf_write_line(context, "}");
}
if (material->has_specular)
{
const cgltf_specular* params = &material->specular;
cgltf_write_line(context, "\"KHR_materials_specular\": {");
CGLTF_WRITE_TEXTURE_INFO("specularTexture", params->specular_texture);
cgltf_write_floatprop(context, "specularFactor", params->specular_factor, 1.0f);
if (cgltf_check_floatarray(params->specular_color_factor, 3, 1.0f))
{
cgltf_write_floatarrayprop(context, "specularColorFactor", params->specular_color_factor, 3);
}
cgltf_write_line(context, "}");
}
if (material->has_transmission)
{
const cgltf_transmission* params = &material->transmission;
Expand Down Expand Up @@ -930,6 +948,9 @@ static void cgltf_write_extensions(cgltf_write_context* context, uint32_t extens
if (extension_flags & CGLTF_EXTENSION_FLAG_MATERIALS_IOR) {
cgltf_write_stritem(context, "KHR_materials_ior");
}
if (extension_flags & CGLTF_EXTENSION_FLAG_MATERIALS_SPECULAR) {
cgltf_write_stritem(context, "KHR_materials_specular");
}
if (extension_flags & CGLTF_EXTENSION_FLAG_MATERIALS_TRANSMISSION) {
cgltf_write_stritem(context, "KHR_materials_transmission");
}
Expand Down

0 comments on commit 468ad38

Please sign in to comment.