1
0
Fork 0
forked from fte/fteqw

Parse gltf2's KHR_materials_transmission and KHR_materials_volume extensions, so eukara can figure out the glsl for it.

This commit is contained in:
Shpoike 2024-12-28 12:11:24 +00:00
parent 249ff8777b
commit 59c0c8857a
8 changed files with 159 additions and 26 deletions

View file

@ -388,6 +388,8 @@ typedef struct texnums_s {
texid_t reflectmask; //2d, defines how reflective it is (for cubemap reflections) texid_t reflectmask; //2d, defines how reflective it is (for cubemap reflections)
texid_t displacement; //2d, alternative to bump.a, eg R16[F] for offsetmapping or tessellation texid_t displacement; //2d, alternative to bump.a, eg R16[F] for offsetmapping or tessellation
texid_t occlusion; //2d, occlusion map... only red is used. texid_t occlusion; //2d, occlusion map... only red is used.
texid_t transmission; //2d, multiplier for transmissionfactor... only red is used.
texid_t thickness; //2d, multiplier for thicknessfactor... only green is used.
//the material's pushconstants. vulkan guarentees only 128 bytes. so 8 vec4s. note that lmscales should want 4 of them... //the material's pushconstants. vulkan guarentees only 128 bytes. so 8 vec4s. note that lmscales should want 4 of them...
/*struct /*struct

View file

@ -1307,6 +1307,18 @@ static void Shader_BindTextureForPass(int tmu, const shaderpass_t *pass)
else else
t = r_whiteimage; t = r_whiteimage;
break; break;
case T_GEN_TRANSMISSION:
if (shaderstate.curtexnums && TEXLOADED(shaderstate.curtexnums->transmission))
t = shaderstate.curtexnums->transmission;
else
t = r_whiteimage;
break;
case T_GEN_THICKNESS:
if (shaderstate.curtexnums && TEXLOADED(shaderstate.curtexnums->thickness))
t = shaderstate.curtexnums->thickness;
else
t = r_whiteimage;
break;
case T_GEN_SHADOWMAP: case T_GEN_SHADOWMAP:
t = shaderstate.curshadowmap; t = shaderstate.curshadowmap;
break; break;

View file

@ -1415,6 +1415,8 @@ const struct sh_defaultsamplers_s sh_defaultsamplers[] =
{"s_reflectmask", 1u<<S_REFLECTMASK}, {"s_reflectmask", 1u<<S_REFLECTMASK},
{"s_displacement", 1u<<S_DISPLACEMENT}, {"s_displacement", 1u<<S_DISPLACEMENT},
{"s_occlusion", 1u<<S_OCCLUSION}, {"s_occlusion", 1u<<S_OCCLUSION},
{"s_transmission", 1u<<S_TRANSMISSION},
{"s_thickness", 1u<<S_THICKNESS},
{"s_lightmap", 1u<<S_LIGHTMAP0}, {"s_lightmap", 1u<<S_LIGHTMAP0},
{"s_deluxemap", 1u<<S_DELUXEMAP0}, {"s_deluxemap", 1u<<S_DELUXEMAP0},
#if MAXRLIGHTMAPS > 1 #if MAXRLIGHTMAPS > 1
@ -2627,7 +2629,7 @@ static void Shader_ReflectCube(parsestate_t *ps, const char **ptr)
static void Shader_ReflectMask(parsestate_t *ps, const char **ptr) static void Shader_ReflectMask(parsestate_t *ps, const char **ptr)
{ {
char *token = Shader_ParseSensString(ptr); char *token = Shader_ParseSensString(ptr);
unsigned int flags = Shader_SetImageFlags (ps, ps->pass, &token, 0); unsigned int flags = Shader_SetImageFlags (ps, ps->pass, &token, IF_NOSRGB);
ps->s->defaulttextures->reflectmask = Shader_FindImage(ps, token, flags); ps->s->defaulttextures->reflectmask = Shader_FindImage(ps, token, flags);
} }
@ -2675,6 +2677,18 @@ static void Shader_DisplacementMap(parsestate_t *ps, const char **ptr)
unsigned int flags = Shader_SetImageFlags (ps, ps->pass, &token, IF_NOSRGB); unsigned int flags = Shader_SetImageFlags (ps, ps->pass, &token, IF_NOSRGB);
ps->s->defaulttextures->displacement = Shader_FindImage(ps, token, flags); ps->s->defaulttextures->displacement = Shader_FindImage(ps, token, flags);
} }
static void Shader_TransmissionMap(parsestate_t *ps, const char **ptr)
{
char *token = Shader_ParseSensString(ptr);
unsigned int flags = Shader_SetImageFlags (ps, ps->pass, &token, IF_NOSRGB);
ps->s->defaulttextures->transmission = Shader_FindImage(ps, token, flags);
}
static void Shader_ThicknessMap(parsestate_t *ps, const char **ptr)
{
char *token = Shader_ParseSensString(ptr);
unsigned int flags = Shader_SetImageFlags (ps, ps->pass, &token, IF_NOSRGB);
ps->s->defaulttextures->thickness = Shader_FindImage(ps, token, flags);
}
static void Shaderpass_QF_Material(parsestate_t *ps, const char **ptr) static void Shaderpass_QF_Material(parsestate_t *ps, const char **ptr)
{ //qf_material BASETEXTURE NORMALMAP SPECULARMAP { //qf_material BASETEXTURE NORMALMAP SPECULARMAP
@ -2835,6 +2849,23 @@ static void Shader_FactorEmit(parsestate_t *ps, const char **ptr)
shader->factors[MATERIAL_FACTOR_EMIT][2] = Shader_ParseFloat(shader, ptr, 1); shader->factors[MATERIAL_FACTOR_EMIT][2] = Shader_ParseFloat(shader, ptr, 1);
shader->factors[MATERIAL_FACTOR_EMIT][3] = Shader_ParseFloat(shader, ptr, 1); shader->factors[MATERIAL_FACTOR_EMIT][3] = Shader_ParseFloat(shader, ptr, 1);
} }
static void Shader_FactorTransmission(parsestate_t *ps, const char **ptr)
{
shader_t *shader = ps->s;
shader->factors[MATERIAL_FACTOR_TRANSMISSION][0] = Shader_ParseFloat(shader, ptr, 1);
// shader->factors[MATERIAL_FACTOR_TRANSMISSION][1] = the volume distance;
shader->factors[MATERIAL_FACTOR_TRANSMISSION][2] = 0;
shader->factors[MATERIAL_FACTOR_TRANSMISSION][3] = 0;
}
static void Shader_FactorVolume(parsestate_t *ps, const char **ptr)
{
shader_t *shader = ps->s;
shader->factors[MATERIAL_FACTOR_VOLUME][0] = Shader_ParseFloat(shader, ptr, 1); //r
shader->factors[MATERIAL_FACTOR_VOLUME][1] = Shader_ParseFloat(shader, ptr, 1); //g
shader->factors[MATERIAL_FACTOR_VOLUME][2] = Shader_ParseFloat(shader, ptr, 1); //b
shader->factors[MATERIAL_FACTOR_VOLUME][3] = Shader_ParseFloat(shader, ptr, 1); //factor
shader->factors[MATERIAL_FACTOR_TRANSMISSION][1] = Shader_ParseFloat(shader, ptr, 1); //distance
}
static void Shader_BEMode(parsestate_t *ps, const char **ptr) static void Shader_BEMode(parsestate_t *ps, const char **ptr)
{ {
@ -2965,11 +2996,15 @@ static shaderkey_t shaderkeys[] =
{"lowermap", Shader_LowerMap, "fte"}, {"lowermap", Shader_LowerMap, "fte"},
{"reflectmask", Shader_ReflectMask, "fte"}, {"reflectmask", Shader_ReflectMask, "fte"},
{"displacementmap", Shader_DisplacementMap, "fte"}, {"displacementmap", Shader_DisplacementMap, "fte"},
{"transmissionmap", Shader_TransmissionMap, "fte"},
{"thicknessmap", Shader_ThicknessMap, "fte"},
{"portalfboscale", Shader_PortalFBOScale, "fte"}, //portal/mirror/refraction/reflection FBOs are resized by this scale {"portalfboscale", Shader_PortalFBOScale, "fte"}, //portal/mirror/refraction/reflection FBOs are resized by this scale
{"basefactor", Shader_FactorBase, "fte"}, //material scalers for glsl {"basefactor", Shader_FactorBase, "fte"}, //material scalers for glsl
{"specularfactor", Shader_FactorSpec, "fte"}, //material scalers for glsl {"specularfactor", Shader_FactorSpec, "fte"}, //material scalers for glsl
{"fullbrightfactor", Shader_FactorEmit, "fte"}, //material scalers for glsl {"fullbrightfactor", Shader_FactorEmit, "fte"}, //material scalers for glsl
{"fte_transmissionfactor",Shader_FactorTransmission,"fte"}, //material scalers for glsl
{"fte_volumefactor", Shader_FactorVolume, "fte"}, //material scalers for glsl
//TODO: PBR textures... //TODO: PBR textures...
// {"albedomap", Shader_DiffuseMap, "fte"}, //rgb(a) // {"albedomap", Shader_DiffuseMap, "fte"}, //rgb(a)
@ -4775,16 +4810,18 @@ static void Shader_FixupProgPasses(parsestate_t *ps, shaderpass_t *pass)
{T_GEN_REFLECTMASK, 0}, //10 {T_GEN_REFLECTMASK, 0}, //10
{T_GEN_DISPLACEMENT, SHADER_HASDISPLACEMENT},//11 {T_GEN_DISPLACEMENT, SHADER_HASDISPLACEMENT},//11
{T_GEN_OCCLUSION, 0}, //12 {T_GEN_OCCLUSION, 0}, //12
{T_GEN_TRANSMISSION, 0}, //13
{T_GEN_THICKNESS, 0}, //14
// {T_GEN_REFLECTION, SHADER_HASREFLECT}, // // {T_GEN_REFLECTION, SHADER_HASREFLECT}, //
// {T_GEN_REFRACTION, SHADER_HASREFRACT}, // // {T_GEN_REFRACTION, SHADER_HASREFRACT}, //
// {T_GEN_REFRACTIONDEPTH, SHADER_HASREFRACTDEPTH},// // {T_GEN_REFRACTIONDEPTH, SHADER_HASREFRACTDEPTH},//
// {T_GEN_RIPPLEMAP, SHADER_HASRIPPLEMAP}, // // {T_GEN_RIPPLEMAP, SHADER_HASRIPPLEMAP}, //
//batch //batch
{T_GEN_LIGHTMAP, SHADER_HASLIGHTMAP}, //13 {T_GEN_LIGHTMAP, SHADER_HASLIGHTMAP}, //15
{T_GEN_DELUXMAP, 0}, //14 {T_GEN_DELUXMAP, 0}, //16
//more lightmaps //15,16,17 //more lightmaps //17,18,19
//mode deluxemaps //18,19,20 //mode deluxemaps //20,21,22
}; };
#ifdef HAVE_MEDIA_DECODER #ifdef HAVE_MEDIA_DECODER
@ -5976,16 +6013,18 @@ done:;
{T_GEN_REFLECTMASK, 0}, //10 {T_GEN_REFLECTMASK, 0}, //10
{T_GEN_DISPLACEMENT, SHADER_HASDISPLACEMENT},//11 {T_GEN_DISPLACEMENT, SHADER_HASDISPLACEMENT},//11
{T_GEN_OCCLUSION, 0}, //12 {T_GEN_OCCLUSION, 0}, //12
{T_GEN_TRANSMISSION, 0}, //13
{T_GEN_THICKNESS, 0}, //14
// {T_GEN_REFLECTION, SHADER_HASREFLECT}, // // {T_GEN_REFLECTION, SHADER_HASREFLECT}, //
// {T_GEN_REFRACTION, SHADER_HASREFRACT}, // // {T_GEN_REFRACTION, SHADER_HASREFRACT}, //
// {T_GEN_REFRACTIONDEPTH, SHADER_HASREFRACTDEPTH},// // {T_GEN_REFRACTIONDEPTH, SHADER_HASREFRACTDEPTH},//
// {T_GEN_RIPPLEMAP, SHADER_HASRIPPLEMAP}, // // {T_GEN_RIPPLEMAP, SHADER_HASRIPPLEMAP}, //
//batch //batch
{T_GEN_LIGHTMAP, SHADER_HASLIGHTMAP}, //13 {T_GEN_LIGHTMAP, SHADER_HASLIGHTMAP}, //15
{T_GEN_DELUXMAP, 0}, //14 {T_GEN_DELUXMAP, 0}, //16
//more lightmaps //15,16,17 //more lightmaps //17,18,19
//mode deluxemaps //18,19,20 //mode deluxemaps //20,21,22
}; };
#ifdef HAVE_MEDIA_DECODER #ifdef HAVE_MEDIA_DECODER
@ -8086,6 +8125,8 @@ static char *Shader_DecomposeSubPass(char *o, shader_t *s, shaderpass_t *p, qboo
case T_GEN_REFLECTMASK: Shader_DecomposeSubPassMap(o, s, "map $reflectmask", s->defaulttextures[0].reflectmask); break; case T_GEN_REFLECTMASK: Shader_DecomposeSubPassMap(o, s, "map $reflectmask", s->defaulttextures[0].reflectmask); break;
case T_GEN_DISPLACEMENT: Shader_DecomposeSubPassMap(o, s, "map $displacement", s->defaulttextures[0].displacement); break; case T_GEN_DISPLACEMENT: Shader_DecomposeSubPassMap(o, s, "map $displacement", s->defaulttextures[0].displacement); break;
case T_GEN_OCCLUSION: Shader_DecomposeSubPassMap(o, s, "map $occlusion", s->defaulttextures[0].occlusion); break; case T_GEN_OCCLUSION: Shader_DecomposeSubPassMap(o, s, "map $occlusion", s->defaulttextures[0].occlusion); break;
case T_GEN_TRANSMISSION: Shader_DecomposeSubPassMap(o, s, "map $transmission", s->defaulttextures[0].transmission); break;
case T_GEN_THICKNESS: Shader_DecomposeSubPassMap(o, s, "map $thickness", s->defaulttextures[0].thickness); break;
case T_GEN_CURRENTRENDER: sprintf(o, "map $currentrender "); break; case T_GEN_CURRENTRENDER: sprintf(o, "map $currentrender "); break;
case T_GEN_SOURCECOLOUR: sprintf(o, "map $sourcecolour"); break; case T_GEN_SOURCECOLOUR: sprintf(o, "map $sourcecolour"); break;
case T_GEN_SOURCEDEPTH: sprintf(o, "map $sourcedepth"); break; case T_GEN_SOURCEDEPTH: sprintf(o, "map $sourcedepth"); break;

View file

@ -1491,14 +1491,24 @@ static const char *glsl_hdrs[] =
#endif #endif
#endif #endif
"#if defined(ORM) || defined(SG)\n" "#if defined(ORM) || defined(SG)\n"
"uniform vec4 factors[3];\n" "uniform vec4 factors[5];\n"
"#define factor_base factors[0]\n" "#define factor_base factors[0]\n"
"#define factor_spec factors[1]\n" "#define factor_spec factors[1]\n"
"#define factor_emit factors[2]\n" "#define factor_emit factors[2]\n"
"#define factor_transmission factors[3].r\n"
"#define factor_volume_distance factors[3].g\n"
// "#define factor_? factors[3].b\n"
// "#define factor_? factors[3].a\n"
"#define factor_volume_rgb factors[4].rgb\n"
"#define factor_volume_thickness factors[4].a\n"
"#else\n" "#else\n"
"#define factor_base vec4(1.0)\n" "#define factor_base vec4(1.0)\n"
"#define factor_spec vec4(1.0)\n" "#define factor_spec vec4(1.0)\n"
"#define factor_emit vec4(1.0)\n" "#define factor_emit vec4(1.0)\n"
/*"#define factor_transmission 0.0\n"
"#define factor_volume_distance 0.0\n"
"#define factor_volume_rgb vec3(1.0)\n"
"#define factor_volume_thickness 0.0\n"*/
"#endif\n" "#endif\n"
"#ifdef USEUBOS\n" "#ifdef USEUBOS\n"
"layout(std140) uniform u_lightinfo\n" "layout(std140) uniform u_lightinfo\n"

View file

@ -274,6 +274,8 @@ typedef struct shaderpass_s {
T_GEN_REFLECTMASK, //dpreflectcube mask T_GEN_REFLECTMASK, //dpreflectcube mask
T_GEN_DISPLACEMENT, //displacement texture (probably half-float or something so higher precision than normalmap.a) T_GEN_DISPLACEMENT, //displacement texture (probably half-float or something so higher precision than normalmap.a)
T_GEN_OCCLUSION, //occlusion mask (instead of baking it into the texture itself, required for correct pbr) T_GEN_OCCLUSION, //occlusion mask (instead of baking it into the texture itself, required for correct pbr)
T_GEN_TRANSMISSION, //.r fancy opacity mask (still contributes its own colour over the top, for KHR_materials_transmission)
T_GEN_THICKNESS, //.g depth mask (could be replaced with raytracing, for KHR_materials_volume)
T_GEN_CURRENTRENDER,//copy the current screen to a texture, and draw that T_GEN_CURRENTRENDER,//copy the current screen to a texture, and draw that
@ -698,7 +700,9 @@ struct shader_s
#define MATERIAL_FACTOR_BASE 0 #define MATERIAL_FACTOR_BASE 0
#define MATERIAL_FACTOR_SPEC 1 #define MATERIAL_FACTOR_SPEC 1
#define MATERIAL_FACTOR_EMIT 2 #define MATERIAL_FACTOR_EMIT 2
#define MATERIAL_FACTOR_COUNT 3 #define MATERIAL_FACTOR_TRANSMISSION 3
#define MATERIAL_FACTOR_VOLUME 4
#define MATERIAL_FACTOR_COUNT 5
vec4_t factors[MATERIAL_FACTOR_COUNT]; vec4_t factors[MATERIAL_FACTOR_COUNT];
//arranged as a series of vec4s //arranged as a series of vec4s
@ -877,15 +881,17 @@ enum
S_REFLECTMASK = 10, S_REFLECTMASK = 10,
S_DISPLACEMENT = 11, S_DISPLACEMENT = 11,
S_OCCLUSION = 12, S_OCCLUSION = 12,
S_LIGHTMAP0 = 13, S_TRANSMISSION = 13,
S_DELUXEMAP0 = 14, S_THICKNESS = 14,
S_LIGHTMAP0 = 15,
S_DELUXEMAP0 = 16,
#if MAXRLIGHTMAPS > 1 #if MAXRLIGHTMAPS > 1
S_LIGHTMAP1 = 15, S_LIGHTMAP1 = 17,
S_LIGHTMAP2 = 16, S_LIGHTMAP2 = 18,
S_LIGHTMAP3 = 17, S_LIGHTMAP3 = 19,
S_DELUXEMAP1 = 18, S_DELUXEMAP1 = 20,
S_DELUXEMAP2 = 19, S_DELUXEMAP2 = 21,
S_DELUXEMAP3 = 20, S_DELUXEMAP3 = 22,
#endif #endif
}; };
extern const struct sh_defaultsamplers_s extern const struct sh_defaultsamplers_s

View file

@ -14,6 +14,8 @@
!!samps !EIGHTBIT diffuse normalmap specular fullbright upper lower reflectmask reflectcube !!samps !EIGHTBIT diffuse normalmap specular fullbright upper lower reflectmask reflectcube
!!samps =EIGHTBIT paletted 1 !!samps =EIGHTBIT paletted 1
!!samps =OCCLUDE occlusion !!samps =OCCLUDE occlusion
!!samps =USE_TRANSMISSION transmission //only .r valid, multiplier for factor_transmission
!!samps =USE_VOLUME thickness //only .g valid, multiplier for factor_volume_thickness, combined with factor_volume_rgb+factor_volume_distance(average distance travelled in metres)
//!!permu VC // adds rgba vertex colour multipliers //!!permu VC // adds rgba vertex colour multipliers
//!!permu SPECULAR // auto-added when gl_specular>0 //!!permu SPECULAR // auto-added when gl_specular>0
//!!permu OFFSETMAPPING // auto-added when r_glsl_offsetmapping is set //!!permu OFFSETMAPPING // auto-added when r_glsl_offsetmapping is set

View file

@ -1588,10 +1588,14 @@ static texid_t SelectPassTexture(const shaderpass_t *pass)
return r_blackcubeimage; //FIXME return r_blackcubeimage; //FIXME
case T_GEN_REFLECTMASK: case T_GEN_REFLECTMASK:
return shaderstate.curtexnums->reflectmask; return shaderstate.curtexnums->reflectmask;
case T_GEN_OCCLUSION:
return shaderstate.curtexnums->occlusion;
case T_GEN_DISPLACEMENT: case T_GEN_DISPLACEMENT:
return shaderstate.curtexnums->displacement; return shaderstate.curtexnums->displacement;
case T_GEN_OCCLUSION:
return shaderstate.curtexnums->occlusion;
case T_GEN_TRANSMISSION:
return shaderstate.curtexnums->transmission;
case T_GEN_THICKNESS:
return shaderstate.curtexnums->thickness;
case T_GEN_ANIMMAP: case T_GEN_ANIMMAP:
return pass->anim_frames[(int)(pass->anim_fps * shaderstate.curtime) % pass->anim_numframes]; return pass->anim_frames[(int)(pass->anim_fps * shaderstate.curtime) % pass->anim_numframes];
@ -3172,6 +3176,10 @@ static qboolean BE_SetupMeshProgram(program_t *p, shaderpass_t *pass, unsigned i
BE_SetupTextureDescriptor(shaderstate.curtexnums->displacement, r_whiteimage, set, descs, desc++, img++); BE_SetupTextureDescriptor(shaderstate.curtexnums->displacement, r_whiteimage, set, descs, desc++, img++);
if (p->defaulttextures & (1u<<S_OCCLUSION)) if (p->defaulttextures & (1u<<S_OCCLUSION))
BE_SetupTextureDescriptor(shaderstate.curtexnums->occlusion, r_whiteimage, set, descs, desc++, img++); BE_SetupTextureDescriptor(shaderstate.curtexnums->occlusion, r_whiteimage, set, descs, desc++, img++);
if (p->defaulttextures & (1u<<S_TRANSMISSION))
BE_SetupTextureDescriptor(shaderstate.curtexnums->transmission, r_whiteimage, set, descs, desc++, img++);
if (p->defaulttextures & (1u<<S_THICKNESS))
BE_SetupTextureDescriptor(shaderstate.curtexnums->thickness, r_whiteimage, set, descs, desc++, img++);
//batch //batch
if (p->defaulttextures & (1u<<S_LIGHTMAP0)) if (p->defaulttextures & (1u<<S_LIGHTMAP0))

View file

@ -1533,6 +1533,7 @@ static void GLTF_LoadMaterial(gltf_t *gltf, json_t *materialid, galiasskin_t *re
const char *t; const char *t;
json_t *nam, *unlit, *pbrsg, *pbrmr, *blinn; json_t *nam, *unlit, *pbrsg, *pbrmr, *blinn;
json_t *transmission, *volume;
nam = JSON_FindChild(mat, "name"); nam = JSON_FindChild(mat, "name");
unlit = JSON_FindChild(mat, "extensions.KHR_materials_unlit"); unlit = JSON_FindChild(mat, "extensions.KHR_materials_unlit");
@ -1540,6 +1541,22 @@ static void GLTF_LoadMaterial(gltf_t *gltf, json_t *materialid, galiasskin_t *re
pbrmr = JSON_FindChild(mat, "pbrMetallicRoughness"); pbrmr = JSON_FindChild(mat, "pbrMetallicRoughness");
blinn = JSON_FindChild(mat, "extensions.KHR_materials_cmnBlinnPhong"); blinn = JSON_FindChild(mat, "extensions.KHR_materials_cmnBlinnPhong");
transmission = JSON_FindChild(mat, "extensions.KHR_materials_transmission");
volume = JSON_FindChild(mat, "extensions.KHR_materials_volume");
if (volume && !transmission)
{
if (gltf->warnlimit --> 0)
Con_Printf(CON_WARNING"%s: KHR_materials_volume without KHR_materials_transmission\n", gltf->mod->name);
volume = NULL;
}
if (transmission && (unlit || pbrsg || blinn) && !pbrmr)
{
if (gltf->warnlimit --> 0)
Con_Printf(CON_WARNING"%s: KHR_materials_transmission without pbrMetallicRoughness\n", gltf->mod->name);
transmission = volume = NULL;
}
doubleSided = JSON_GetInteger(mat, "doubleSided", false); doubleSided = JSON_GetInteger(mat, "doubleSided", false);
alphaCutoff = JSON_GetFloat(mat, "alphaCutoff", 0.5); alphaCutoff = JSON_GetFloat(mat, "alphaCutoff", 0.5);
t = JSON_GetString(mat, "alphaMode", tmp, sizeof(tmp), "OPAQUE"); t = JSON_GetString(mat, "alphaMode", tmp, sizeof(tmp), "OPAQUE");
@ -1757,10 +1774,30 @@ static void GLTF_LoadMaterial(gltf_t *gltf, json_t *materialid, galiasskin_t *re
else //else depend upon specularfactor else //else depend upon specularfactor
ret->frame->texnums.specular = modfuncs->GetTexture("$whiteimage", NULL, IF_NOMIPMAP|IF_NOPICMIP|IF_NEAREST|IF_NOGAMMA, NULL, NULL, 0, 0, TF_INVALID); ret->frame->texnums.specular = modfuncs->GetTexture("$whiteimage", NULL, IF_NOMIPMAP|IF_NOPICMIP|IF_NEAREST|IF_NOGAMMA, NULL, NULL, 0, 0, TF_INVALID);
if (transmission)
{
n = JSON_FindChild(transmission, "transmissionTexture.index"); //.r = factor
if (n)
ret->frame->texnums.transmission = GLTF_LoadTexture(gltf, n, IF_NOSRGB);
else
ret->frame->texnums.transmission = modfuncs->GetTexture("$whiteimage", NULL, IF_NOMIPMAP|IF_NOPICMIP|IF_NEAREST|IF_NOGAMMA, NULL, NULL, 0, 0, TF_INVALID);
if (volume)
{
n = JSON_FindChild(volume, "thicknessTexture.index"); //.g = thicknessFactor
if (n)
ret->frame->texnums.transmission = GLTF_LoadTexture(gltf, n, IF_NOSRGB);
else
ret->frame->texnums.transmission = modfuncs->GetTexture("$whiteimage", NULL, IF_NOMIPMAP|IF_NOPICMIP|IF_NEAREST|IF_NOGAMMA, NULL, NULL, 0, 0, TF_INVALID);
}
}
#ifndef INFINITY //C99.
#define INFINITY (1.0/0.0)
#endif
Q_snprintf(shader, sizeof(shader), Q_snprintf(shader, sizeof(shader),
"{\n" "{\n"
"%s"//cull "%s"//cull
"program defaultskin" "#ORM" "#VC" "#IOR=%.02f" "%s"/*occlude*/ "%s"/*alphatest*/ "\n" "program defaultskin" "#ORM" "#VC" "#IOR=%.02f" "%s"/*occlude*/ "%s"/*transmission*/ "%s"/*volume*/ "%s"/*alphatest*/ "\n"
"{\n" "{\n"
"map $diffuse\n" "map $diffuse\n"
"%s" //blend "%s" //blend
@ -1769,11 +1806,16 @@ static void GLTF_LoadMaterial(gltf_t *gltf, json_t *materialid, galiasskin_t *re
"fte_basefactor %f %f %f %f\n" "fte_basefactor %f %f %f %f\n"
"fte_specularfactor %f %f %f 1.0\n" "fte_specularfactor %f %f %f 1.0\n"
"fte_fullbrightfactor %f %f %f 1.0\n" "fte_fullbrightfactor %f %f %f 1.0\n"
"fte_transmissionfactor %f\n"
"fte_volumefactor %f %f %f %f %f\n"
"bemode rtlight rtlight_orm\n" "bemode rtlight rtlight_orm\n"
"}\n", "}\n",
doubleSided?"cull disable\n":"", doubleSided?"cull disable\n":"",
ior, ior,
(!occ)?"#NOOCCLUDE":(strcmp(occname,mrtname)?"#OCCLUDE":""), (!occ)?"#NOOCCLUDE":(strcmp(occname,mrtname)?"#OCCLUDE":""),
(transmission?"#USE_TRANSMISSION":""),
(volume?"#USE_VOLUME":""),
alphaCutoffmodifier, alphaCutoffmodifier,
(alphaMode==1)?"":(alphaMode==2)?"blendfunc blend\n":"", (alphaMode==1)?"":(alphaMode==2)?"blendfunc blend\n":"",
vertexcolours?"rgbgen vertex\nalphagen vertex\n":"", vertexcolours?"rgbgen vertex\nalphagen vertex\n":"",
@ -1786,7 +1828,13 @@ static void GLTF_LoadMaterial(gltf_t *gltf, json_t *materialid, galiasskin_t *re
JSON_GetFloat(pbrmr, "roughnessFactor", 1), JSON_GetFloat(pbrmr, "roughnessFactor", 1),
JSON_GetFloat(mat, "emissiveFactor.0", 0), JSON_GetFloat(mat, "emissiveFactor.0", 0),
JSON_GetFloat(mat, "emissiveFactor.1", 0), JSON_GetFloat(mat, "emissiveFactor.1", 0),
JSON_GetFloat(mat, "emissiveFactor.2", 0) JSON_GetFloat(mat, "emissiveFactor.2", 0),
JSON_GetFloat(transmission, "transmissionFactor", 0),
JSON_GetFloat(volume, "attenuationColor.0", 1),
JSON_GetFloat(volume, "attenuationColor.1", 1),
JSON_GetFloat(volume, "attenuationColor.2", 1),
JSON_GetFloat(volume, "thicknessFactor", 0),
JSON_GetFloat(volume, "attenuationDistance", INFINITY)
); );
} }
if (!ret->frame->texnums.bump) if (!ret->frame->texnums.bump)
@ -2970,14 +3018,18 @@ static qboolean GLTF_LoadModel(struct model_s *mod, char *json, size_t jsonsize,
{"KHR_materials_variants", true, false}, {"KHR_materials_variants", true, false},
{"KHR_materials_ior", true, false}, {"KHR_materials_ior", true, false},
{"KHR_materials_transmission", true, true}, //FIXME: requires glsl tweaks.
{"KHR_materials_volume", true, true}, //FOXME: requires glsl tweaks.
#ifdef HAVE_DRACO #ifdef HAVE_DRACO
{"KHR_draco_mesh_compression", true, false}, //probably fatal {"KHR_draco_mesh_compression", true, false}, //probably fatal
#else #else
{"KHR_draco_mesh_compression", false, false}, //probably fatal {"KHR_draco_mesh_compression", false, false}, //probably fatal
#endif #endif
{"KHR_texture_transform", false, false}, //requires glsl tweaks, per texmap. can't use tcmod if its only on the bumpmap etc. {"KHR_texture_transform", false, true}, //requires glsl tweaks, per texmap. can't use tcmod if its only on the bumpmap etc.
{"KHR_materials_sheen", false, false}, //requires glsl tweaks, extra brdf layer in the middle for velvet. {"KHR_materials_sheen", false, true}, //requires glsl tweaks, extra brdf layer in the middle for velvet.
{"KHR_materials_clearcoat", false, false}, //requires glsl tweaks, extra brdf layer over the top for varnish etc. {"KHR_materials_clearcoat", false, true}, //requires glsl tweaks, extra brdf layer over the top for varnish etc.
{NULL} {NULL}
}, *extensions; }, *extensions;
gltf_t gltf; gltf_t gltf;