Support occlusion texture all the way. (#81)
By oversight we had not included occlusionTexture in the core MaterialData. While we're at it, bake occlusion into the red channel of the merged metallic/roughness texture.
This commit is contained in:
parent
362b8bd761
commit
dc8f199d54
|
@ -635,8 +635,9 @@ ModelData *Raw2Gltf(
|
||||||
return (material.textures[usage] >= 0) ? getSimpleTexture(material.textures[usage], "simple") : nullptr;
|
return (material.textures[usage] >= 0) ? getSimpleTexture(material.textures[usage], "simple") : nullptr;
|
||||||
};
|
};
|
||||||
|
|
||||||
TextureData *normalTexture = simpleTex(RAW_TEXTURE_USAGE_NORMAL).get();
|
TextureData *normalTexture = simpleTex(RAW_TEXTURE_USAGE_NORMAL).get();
|
||||||
TextureData *emissiveTexture = simpleTex(RAW_TEXTURE_USAGE_EMISSIVE).get();
|
TextureData *emissiveTexture = simpleTex(RAW_TEXTURE_USAGE_EMISSIVE).get();
|
||||||
|
TextureData *occlusionTexture = nullptr;
|
||||||
|
|
||||||
// acquire derived texture of two RawTextureUsage as *TextData, or nullptr if neither exists
|
// acquire derived texture of two RawTextureUsage as *TextData, or nullptr if neither exists
|
||||||
auto merge2Tex = [&](
|
auto merge2Tex = [&](
|
||||||
|
@ -651,10 +652,24 @@ ModelData *Raw2Gltf(
|
||||||
combine, tag, outputHasAlpha);
|
combine, tag, outputHasAlpha);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// acquire derived texture of two RawTextureUsage as *TextData, or nullptr if neither exists
|
||||||
|
auto merge3Tex = [&](
|
||||||
|
const std::string tag,
|
||||||
|
RawTextureUsage u1,
|
||||||
|
RawTextureUsage u2,
|
||||||
|
RawTextureUsage u3,
|
||||||
|
const pixel_merger &combine,
|
||||||
|
bool outputHasAlpha
|
||||||
|
) -> std::shared_ptr<TextureData> {
|
||||||
|
return getDerivedTexture(
|
||||||
|
{ material.textures[u1], material.textures[u2], material.textures[u3] },
|
||||||
|
combine, tag, outputHasAlpha);
|
||||||
|
};
|
||||||
|
|
||||||
std::shared_ptr<PBRMetallicRoughness> pbrMetRough;
|
std::shared_ptr<PBRMetallicRoughness> pbrMetRough;
|
||||||
if (options.usePBRMetRough) {
|
if (options.usePBRMetRough) {
|
||||||
// albedo is a basic texture, no merging needed
|
// albedo is a basic texture, no merging needed
|
||||||
std::shared_ptr<TextureData> baseColorTex, metRoughTex;
|
std::shared_ptr<TextureData> baseColorTex, aoMetRoughTex;
|
||||||
|
|
||||||
Vec4f diffuseFactor;
|
Vec4f diffuseFactor;
|
||||||
float metallic, roughness;
|
float metallic, roughness;
|
||||||
|
@ -667,9 +682,11 @@ ModelData *Raw2Gltf(
|
||||||
*/
|
*/
|
||||||
RawMetRoughMatProps *props = (RawMetRoughMatProps *) material.info.get();
|
RawMetRoughMatProps *props = (RawMetRoughMatProps *) material.info.get();
|
||||||
// merge metallic into the blue channel and roughness into the green, of a new combinatory texture
|
// merge metallic into the blue channel and roughness into the green, of a new combinatory texture
|
||||||
metRoughTex = merge2Tex("met_rough",
|
aoMetRoughTex = merge3Tex("ao_met_rough",
|
||||||
RAW_TEXTURE_USAGE_METALLIC, RAW_TEXTURE_USAGE_ROUGHNESS,
|
RAW_TEXTURE_USAGE_OCCLUSION, RAW_TEXTURE_USAGE_METALLIC, RAW_TEXTURE_USAGE_ROUGHNESS,
|
||||||
[&](const std::vector<const pixel *> pixels) -> pixel { return { 0, (*pixels[1])[0], (*pixels[0])[0], 0 }; },
|
[&](const std::vector<const pixel *> pixels) -> pixel {
|
||||||
|
return { (*pixels[0])[0], (*pixels[2])[0], (*pixels[1])[0], 0 };
|
||||||
|
},
|
||||||
false);
|
false);
|
||||||
baseColorTex = simpleTex(RAW_TEXTURE_USAGE_ALBEDO);
|
baseColorTex = simpleTex(RAW_TEXTURE_USAGE_ALBEDO);
|
||||||
diffuseFactor = props->diffuseFactor;
|
diffuseFactor = props->diffuseFactor;
|
||||||
|
@ -677,6 +694,10 @@ ModelData *Raw2Gltf(
|
||||||
roughness = props->roughness;
|
roughness = props->roughness;
|
||||||
emissiveFactor = props->emissiveFactor;
|
emissiveFactor = props->emissiveFactor;
|
||||||
emissiveIntensity = props->emissiveIntensity;
|
emissiveIntensity = props->emissiveIntensity;
|
||||||
|
// add the occlusion texture only if actual occlusion pixels exist in the aoNetRough texture.
|
||||||
|
if (material.textures[RAW_TEXTURE_USAGE_OCCLUSION] >= 0) {
|
||||||
|
occlusionTexture = aoMetRoughTex.get();
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
/**
|
/**
|
||||||
* Traditional FBX Material -> PBR Met/Rough glTF.
|
* Traditional FBX Material -> PBR Met/Rough glTF.
|
||||||
|
@ -697,10 +718,9 @@ ModelData *Raw2Gltf(
|
||||||
emissiveFactor = props->emissiveFactor;
|
emissiveFactor = props->emissiveFactor;
|
||||||
emissiveIntensity = 1.0f;
|
emissiveIntensity = 1.0f;
|
||||||
}
|
}
|
||||||
pbrMetRough.reset(new PBRMetallicRoughness(baseColorTex.get(), metRoughTex.get(), diffuseFactor, metallic, roughness));
|
pbrMetRough.reset(new PBRMetallicRoughness(baseColorTex.get(), aoMetRoughTex.get(), diffuseFactor, metallic, roughness));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
std::shared_ptr<KHRCmnUnlitMaterial> khrCmnUnlitMat;
|
std::shared_ptr<KHRCmnUnlitMaterial> khrCmnUnlitMat;
|
||||||
if (options.useKHRMatUnlit) {
|
if (options.useKHRMatUnlit) {
|
||||||
normalTexture = nullptr;
|
normalTexture = nullptr;
|
||||||
|
@ -725,13 +745,14 @@ ModelData *Raw2Gltf(
|
||||||
|
|
||||||
khrCmnUnlitMat.reset(new KHRCmnUnlitMaterial());
|
khrCmnUnlitMat.reset(new KHRCmnUnlitMaterial());
|
||||||
}
|
}
|
||||||
|
if (!occlusionTexture) {
|
||||||
|
occlusionTexture = simpleTex(RAW_TEXTURE_USAGE_OCCLUSION).get();
|
||||||
|
}
|
||||||
|
|
||||||
std::shared_ptr<MaterialData> mData = gltf->materials.hold(
|
std::shared_ptr<MaterialData> mData = gltf->materials.hold(
|
||||||
new MaterialData(
|
new MaterialData(
|
||||||
material.name, isTransparent,
|
material.name, isTransparent, normalTexture, occlusionTexture, emissiveTexture,
|
||||||
normalTexture, emissiveTexture,
|
emissiveFactor * emissiveIntensity, khrCmnUnlitMat, pbrMetRough));
|
||||||
emissiveFactor * emissiveIntensity,
|
|
||||||
khrCmnUnlitMat, pbrMetRough));
|
|
||||||
materialsByName[materialHash(material)] = mData;
|
materialsByName[materialHash(material)] = mData;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -80,6 +80,7 @@ void to_json(json &j, const PBRMetallicRoughness &d)
|
||||||
|
|
||||||
MaterialData::MaterialData(
|
MaterialData::MaterialData(
|
||||||
std::string name, bool isTransparent, const TextureData *normalTexture,
|
std::string name, bool isTransparent, const TextureData *normalTexture,
|
||||||
|
const TextureData *occlusionTexture,
|
||||||
const TextureData *emissiveTexture, const Vec3f & emissiveFactor,
|
const TextureData *emissiveTexture, const Vec3f & emissiveFactor,
|
||||||
std::shared_ptr<KHRCmnUnlitMaterial> const khrCmnConstantMaterial,
|
std::shared_ptr<KHRCmnUnlitMaterial> const khrCmnConstantMaterial,
|
||||||
std::shared_ptr<PBRMetallicRoughness> const pbrMetallicRoughness)
|
std::shared_ptr<PBRMetallicRoughness> const pbrMetallicRoughness)
|
||||||
|
@ -87,6 +88,7 @@ MaterialData::MaterialData(
|
||||||
name(std::move(name)),
|
name(std::move(name)),
|
||||||
isTransparent(isTransparent),
|
isTransparent(isTransparent),
|
||||||
normalTexture(Tex::ref(normalTexture)),
|
normalTexture(Tex::ref(normalTexture)),
|
||||||
|
occlusionTexture(Tex::ref(occlusionTexture)),
|
||||||
emissiveTexture(Tex::ref(emissiveTexture)),
|
emissiveTexture(Tex::ref(emissiveTexture)),
|
||||||
emissiveFactor(clamp(emissiveFactor)),
|
emissiveFactor(clamp(emissiveFactor)),
|
||||||
khrCmnConstantMaterial(khrCmnConstantMaterial),
|
khrCmnConstantMaterial(khrCmnConstantMaterial),
|
||||||
|
@ -102,6 +104,9 @@ json MaterialData::serialize() const
|
||||||
if (normalTexture != nullptr) {
|
if (normalTexture != nullptr) {
|
||||||
result["normalTexture"] = *normalTexture;
|
result["normalTexture"] = *normalTexture;
|
||||||
}
|
}
|
||||||
|
if (occlusionTexture != nullptr) {
|
||||||
|
result["occlusionTexture"] = *occlusionTexture;
|
||||||
|
}
|
||||||
if (emissiveTexture != nullptr) {
|
if (emissiveTexture != nullptr) {
|
||||||
result["emissiveTexture"] = *emissiveTexture;
|
result["emissiveTexture"] = *emissiveTexture;
|
||||||
}
|
}
|
||||||
|
|
|
@ -45,6 +45,7 @@ struct MaterialData : Holdable
|
||||||
{
|
{
|
||||||
MaterialData(
|
MaterialData(
|
||||||
std::string name, bool isTransparent, const TextureData *normalTexture,
|
std::string name, bool isTransparent, const TextureData *normalTexture,
|
||||||
|
const TextureData *occlusionTexture,
|
||||||
const TextureData *emissiveTexture, const Vec3f &emissiveFactor,
|
const TextureData *emissiveTexture, const Vec3f &emissiveFactor,
|
||||||
std::shared_ptr<KHRCmnUnlitMaterial> const khrCmnConstantMaterial,
|
std::shared_ptr<KHRCmnUnlitMaterial> const khrCmnConstantMaterial,
|
||||||
std::shared_ptr<PBRMetallicRoughness> const pbrMetallicRoughness);
|
std::shared_ptr<PBRMetallicRoughness> const pbrMetallicRoughness);
|
||||||
|
@ -54,6 +55,7 @@ struct MaterialData : Holdable
|
||||||
const std::string name;
|
const std::string name;
|
||||||
const bool isTransparent;
|
const bool isTransparent;
|
||||||
const std::unique_ptr<const Tex> normalTexture;
|
const std::unique_ptr<const Tex> normalTexture;
|
||||||
|
const std::unique_ptr<const Tex> occlusionTexture;
|
||||||
const std::unique_ptr<const Tex> emissiveTexture;
|
const std::unique_ptr<const Tex> emissiveTexture;
|
||||||
const Vec3f emissiveFactor;
|
const Vec3f emissiveFactor;
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue