278 lines
14 KiB
C#
278 lines
14 KiB
C#
using System.Collections.Generic;
|
|
using GLTF.Schema;
|
|
using UnityEngine;
|
|
using UnityGLTF.Extensions;
|
|
|
|
namespace UnityGLTF.Plugins
|
|
{
|
|
public class MaterialExtensionsExport: GLTFExportPlugin
|
|
{
|
|
public bool KHR_materials_ior = true;
|
|
public bool KHR_materials_transmission = true;
|
|
public bool KHR_materials_volume = true;
|
|
public bool KHR_materials_iridescence = true;
|
|
public bool KHR_materials_specular = true;
|
|
public bool KHR_materials_clearcoat = true;
|
|
public bool KHR_materials_emissive_strength = true;
|
|
public bool KHR_materials_sheen = true;
|
|
|
|
public override GLTFExportPluginContext CreateInstance(ExportContext context)
|
|
{
|
|
return new MaterialExtensionsExportContext(this);
|
|
}
|
|
|
|
public override string DisplayName => "KHR_materials_* PBR Next Extensions";
|
|
public override string Description =>
|
|
@"Exports various glTF PBR Material model extensions. Supported extensions:
|
|
- KHR_materials_ior
|
|
- KHR_materials_transmission
|
|
- KHR_materials_volume
|
|
- KHR_materials_iridescence
|
|
- KHR_materials_specular
|
|
- KHR_materials_clearcoat
|
|
- KHR_materials_emissive_strength
|
|
- KHR_materials_sheen
|
|
";
|
|
}
|
|
|
|
public class MaterialExtensionsExportContext: GLTFExportPluginContext
|
|
{
|
|
internal readonly MaterialExtensionsExport settings;
|
|
|
|
public MaterialExtensionsExportContext(MaterialExtensionsExport settings)
|
|
{
|
|
this.settings = settings;
|
|
}
|
|
|
|
private static readonly int thicknessTexture = Shader.PropertyToID("thicknessTexture");
|
|
private static readonly int thicknessFactor = Shader.PropertyToID("thicknessFactor");
|
|
private static readonly int attenuationDistance = Shader.PropertyToID("attenuationDistance");
|
|
private static readonly int attenuationColor = Shader.PropertyToID("attenuationColor");
|
|
private static readonly int ior = Shader.PropertyToID("ior");
|
|
private static readonly int transmissionFactor = Shader.PropertyToID("transmissionFactor");
|
|
private static readonly int transmissionTexture = Shader.PropertyToID("transmissionTexture");
|
|
private static readonly int dispersion = Shader.PropertyToID("dispersion");
|
|
|
|
private static readonly int iridescenceFactor = Shader.PropertyToID("iridescenceFactor");
|
|
private static readonly int iridescenceIor = Shader.PropertyToID("iridescenceIor");
|
|
private static readonly int iridescenceThicknessMinimum = Shader.PropertyToID("iridescenceThicknessMinimum");
|
|
private static readonly int iridescenceThicknessMaximum = Shader.PropertyToID("iridescenceThicknessMaximum");
|
|
private static readonly int iridescenceTexture = Shader.PropertyToID("iridescenceTexture");
|
|
private static readonly int iridescenceThicknessTexture = Shader.PropertyToID("iridescenceThicknessTexture");
|
|
|
|
private static readonly int specularFactor = Shader.PropertyToID("specularFactor");
|
|
private static readonly int specularColorFactor = Shader.PropertyToID("specularColorFactor");
|
|
private static readonly int specularTexture = Shader.PropertyToID("specularTexture");
|
|
private static readonly int specularColorTexture = Shader.PropertyToID("specularColorTexture");
|
|
|
|
private static readonly int clearcoatFactor = Shader.PropertyToID("clearcoatFactor");
|
|
private static readonly int clearcoatTexture = Shader.PropertyToID("clearcoatTexture");
|
|
private static readonly int clearcoatRoughnessFactor = Shader.PropertyToID("clearcoatRoughnessFactor");
|
|
private static readonly int clearcoatRoughnessTexture = Shader.PropertyToID("clearcoatRoughnessTexture");
|
|
private static readonly int clearcoatNormalTexture = Shader.PropertyToID("clearcoatNormalTexture");
|
|
|
|
private static readonly int sheenColorFactor = Shader.PropertyToID("sheenColorFactor");
|
|
private static readonly int sheenRoughnessFactor = Shader.PropertyToID("sheenRoughnessFactor");
|
|
private static readonly int sheenColorTexture = Shader.PropertyToID("sheenColorTexture");
|
|
private static readonly int sheenRoughnessTexture = Shader.PropertyToID("sheenRoughnessTexture");
|
|
|
|
public override void AfterMaterialExport(GLTFSceneExporter exporter, GLTFRoot gltfroot, Material material, GLTFMaterial materialnode)
|
|
{
|
|
if (!material) return;
|
|
|
|
var usesTransmission = material.IsKeywordEnabled("_VOLUME_TRANSMISSION_ON") || material.IsKeywordEnabled("_VOLUME_TRANSMISSION_ANDDISPERSION");
|
|
var usesDispersion = material.IsKeywordEnabled("_VOLUME_TRANSMISSION_ANDDISPERSION");
|
|
var usesVolume = material.HasProperty("_VOLUME_ON") && material.GetFloat("_VOLUME_ON") > 0.5f;
|
|
var hasNonDefaultIor = material.HasProperty(ior) && !Mathf.Approximately(material.GetFloat(ior), KHR_materials_ior.DefaultIor);
|
|
var usesIridescence = material.IsKeywordEnabled("_IRIDESCENCE_ON");
|
|
var usesSpecular = material.IsKeywordEnabled("_SPECULAR_ON");
|
|
var usesClearcoat = material.IsKeywordEnabled("_CLEARCOAT_ON");
|
|
var usesSheen = material.IsKeywordEnabled("_SHEEN_ON");
|
|
|
|
if (hasNonDefaultIor && settings.KHR_materials_ior)
|
|
{
|
|
if (materialnode.Extensions == null)
|
|
materialnode.Extensions = new Dictionary<string, IExtension>();
|
|
|
|
var vi = new KHR_materials_ior();
|
|
if (materialnode.Extensions.TryGetValue(KHR_materials_ior_Factory.EXTENSION_NAME, out var vv1))
|
|
vi = (KHR_materials_ior) vv1;
|
|
else
|
|
materialnode.Extensions.Add(KHR_materials_ior_Factory.EXTENSION_NAME, vi);
|
|
|
|
exporter.DeclareExtensionUsage(KHR_materials_ior_Factory.EXTENSION_NAME, false);
|
|
|
|
if (material.HasProperty(ior))
|
|
vi.ior = material.GetFloat(ior);
|
|
}
|
|
|
|
if (usesTransmission && settings.KHR_materials_transmission)
|
|
{
|
|
if (materialnode.Extensions == null)
|
|
materialnode.Extensions = new Dictionary<string, IExtension>();
|
|
|
|
exporter.DeclareExtensionUsage(KHR_materials_transmission_Factory.EXTENSION_NAME, false);
|
|
|
|
// if the material already has an extension, we should get and modify that
|
|
var vt = new KHR_materials_transmission();
|
|
|
|
if (materialnode.Extensions.TryGetValue(KHR_materials_transmission_Factory.EXTENSION_NAME, out var vv2))
|
|
vt = (KHR_materials_transmission) vv2;
|
|
else
|
|
materialnode.Extensions.Add(KHR_materials_transmission_Factory.EXTENSION_NAME, vt);
|
|
|
|
if (material.HasProperty(transmissionFactor))
|
|
vt.transmissionFactor = material.GetFloat(transmissionFactor);
|
|
if (material.HasProperty(transmissionTexture) && material.GetTexture(transmissionTexture))
|
|
vt.transmissionTexture = exporter.ExportTextureInfoWithTextureTransform(material, material.GetTexture(transmissionTexture), nameof(transmissionTexture));
|
|
|
|
if (usesDispersion)
|
|
{
|
|
float dispersionValue = material.GetFloat(dispersion);
|
|
if (dispersionValue > 0)
|
|
{
|
|
exporter.DeclareExtensionUsage(KHR_materials_dispersion_Factory.EXTENSION_NAME, false);
|
|
// if the material already has an extension, we should get and modify that
|
|
var vd = new KHR_materials_dispersion();
|
|
|
|
if (materialnode.Extensions.TryGetValue(KHR_materials_dispersion_Factory.EXTENSION_NAME, out var vd2))
|
|
vd = (KHR_materials_dispersion) vd2;
|
|
else
|
|
materialnode.Extensions.Add(KHR_materials_dispersion_Factory.EXTENSION_NAME, vd);
|
|
|
|
vd.dispersion = dispersionValue;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (usesVolume && settings.KHR_materials_volume)
|
|
{
|
|
if (materialnode.Extensions == null)
|
|
materialnode.Extensions = new Dictionary<string, IExtension>();
|
|
|
|
exporter.DeclareExtensionUsage(KHR_materials_volume_Factory.EXTENSION_NAME, false);
|
|
|
|
// if the material already has an extension, we should get and modify that
|
|
var ve = new KHR_materials_volume();
|
|
|
|
if (materialnode.Extensions.TryGetValue(KHR_materials_volume_Factory.EXTENSION_NAME, out var vv0))
|
|
ve = (KHR_materials_volume)vv0;
|
|
else
|
|
materialnode.Extensions.Add(KHR_materials_volume_Factory.EXTENSION_NAME, ve);
|
|
|
|
if (material.HasProperty(thicknessFactor))
|
|
ve.thicknessFactor = material.GetFloat(thicknessFactor);
|
|
if (material.HasProperty(thicknessTexture) && material.GetTexture(thicknessTexture))
|
|
ve.thicknessTexture = exporter.ExportTextureInfoWithTextureTransform(material, material.GetTexture(thicknessTexture), nameof(thicknessTexture));
|
|
if (material.HasProperty(attenuationDistance))
|
|
ve.attenuationDistance = material.GetFloat(attenuationDistance);
|
|
if (material.HasProperty(attenuationColor))
|
|
ve.attenuationColor = material.GetColor(attenuationColor).ToNumericsColorRaw();
|
|
}
|
|
|
|
if (usesIridescence && settings.KHR_materials_iridescence)
|
|
{
|
|
exporter.DeclareExtensionUsage(KHR_materials_iridescence_Factory.EXTENSION_NAME, false);
|
|
|
|
if (materialnode.Extensions == null)
|
|
materialnode.Extensions = new Dictionary<string, IExtension>();
|
|
|
|
var vir = new KHR_materials_iridescence();
|
|
|
|
if (materialnode.Extensions.TryGetValue(KHR_materials_iridescence_Factory.EXTENSION_NAME, out var vv0))
|
|
vir = (KHR_materials_iridescence) vv0;
|
|
else
|
|
materialnode.Extensions.Add(KHR_materials_iridescence_Factory.EXTENSION_NAME, vir);
|
|
|
|
if (material.HasProperty(iridescenceFactor))
|
|
vir.iridescenceFactor = material.GetFloat(iridescenceFactor);
|
|
if (material.HasProperty(iridescenceIor))
|
|
vir.iridescenceIor = material.GetFloat(iridescenceIor);
|
|
if (material.HasProperty(iridescenceThicknessMinimum))
|
|
vir.iridescenceThicknessMinimum = material.GetFloat(iridescenceThicknessMinimum);
|
|
if (material.HasProperty(iridescenceThicknessMaximum))
|
|
vir.iridescenceThicknessMaximum = material.GetFloat(iridescenceThicknessMaximum);
|
|
if (material.HasProperty(iridescenceTexture) && material.GetTexture(iridescenceTexture))
|
|
vir.iridescenceTexture = exporter.ExportTextureInfoWithTextureTransform(material, material.GetTexture(iridescenceTexture), nameof(iridescenceTexture));
|
|
if (material.HasProperty(iridescenceThicknessTexture) && material.GetTexture(iridescenceThicknessTexture))
|
|
vir.iridescenceThicknessTexture = exporter.ExportTextureInfoWithTextureTransform(material, material.GetTexture(iridescenceThicknessTexture), nameof(iridescenceThicknessTexture));
|
|
}
|
|
|
|
if (usesSpecular && settings.KHR_materials_specular)
|
|
{
|
|
exporter.DeclareExtensionUsage(KHR_materials_specular_Factory.EXTENSION_NAME, false);
|
|
|
|
if (materialnode.Extensions == null)
|
|
materialnode.Extensions = new Dictionary<string, IExtension>();
|
|
|
|
var vir = new KHR_materials_specular();
|
|
|
|
if (materialnode.Extensions.TryGetValue(KHR_materials_specular_Factory.EXTENSION_NAME, out var vv0))
|
|
vir = (KHR_materials_specular) vv0;
|
|
else
|
|
materialnode.Extensions.Add(KHR_materials_specular_Factory.EXTENSION_NAME, vir);
|
|
|
|
if (material.HasProperty(specularFactor))
|
|
vir.specularFactor = material.GetFloat(specularFactor);
|
|
if (material.HasProperty(specularColorFactor))
|
|
vir.specularColorFactor = material.GetColor(specularColorFactor).ToNumericsColorRaw();
|
|
if (material.HasProperty(specularTexture) && material.GetTexture(specularTexture))
|
|
vir.specularTexture = exporter.ExportTextureInfoWithTextureTransform(material, material.GetTexture(specularTexture), nameof(specularTexture));
|
|
if (material.HasProperty(specularColorTexture) && material.GetTexture(specularColorTexture))
|
|
vir.specularColorTexture = exporter.ExportTextureInfoWithTextureTransform(material, material.GetTexture(specularColorTexture), nameof(specularColorTexture));
|
|
}
|
|
|
|
if (usesClearcoat && settings.KHR_materials_clearcoat)
|
|
{
|
|
exporter.DeclareExtensionUsage(KHR_materials_clearcoat_Factory.EXTENSION_NAME, false);
|
|
|
|
if (materialnode.Extensions == null)
|
|
materialnode.Extensions = new Dictionary<string, IExtension>();
|
|
|
|
var cc = new KHR_materials_clearcoat();
|
|
|
|
if (materialnode.Extensions.TryGetValue(KHR_materials_clearcoat_Factory.EXTENSION_NAME, out var vv0))
|
|
cc = (KHR_materials_clearcoat) vv0;
|
|
else
|
|
materialnode.Extensions.Add(KHR_materials_clearcoat_Factory.EXTENSION_NAME, cc);
|
|
|
|
if (material.HasProperty(clearcoatFactor))
|
|
cc.clearcoatFactor = material.GetFloat(clearcoatFactor);
|
|
if (material.HasProperty(clearcoatTexture))
|
|
cc.clearcoatTexture = exporter.ExportTextureInfoWithTextureTransform(material, material.GetTexture(clearcoatTexture), nameof(clearcoatTexture));
|
|
if (material.HasProperty(clearcoatRoughnessFactor))
|
|
cc.clearcoatRoughnessFactor = material.GetFloat(clearcoatRoughnessFactor);
|
|
if (material.HasProperty(clearcoatRoughnessTexture))
|
|
cc.clearcoatRoughnessTexture = exporter.ExportTextureInfoWithTextureTransform(material, material.GetTexture(clearcoatRoughnessTexture), nameof(clearcoatRoughnessTexture));
|
|
if (material.HasProperty(clearcoatNormalTexture))
|
|
cc.clearcoatNormalTexture = exporter.ExportTextureInfoWithTextureTransform(material, material.GetTexture(clearcoatNormalTexture), nameof(clearcoatNormalTexture));
|
|
}
|
|
|
|
if (usesSheen && settings.KHR_materials_sheen)
|
|
{
|
|
exporter.DeclareExtensionUsage(KHR_materials_sheen_Factory.EXTENSION_NAME, false);
|
|
|
|
if (materialnode.Extensions == null)
|
|
materialnode.Extensions = new Dictionary<string, IExtension>();
|
|
|
|
var cc = new KHR_materials_sheen();
|
|
|
|
if (materialnode.Extensions.TryGetValue(KHR_materials_sheen_Factory.EXTENSION_NAME, out var vv0))
|
|
cc = (KHR_materials_sheen) vv0;
|
|
else
|
|
materialnode.Extensions.Add(KHR_materials_sheen_Factory.EXTENSION_NAME, cc);
|
|
|
|
if (material.HasProperty(sheenColorFactor))
|
|
cc.sheenColorFactor = material.GetColor(sheenColorFactor).ToNumericsColorRaw();
|
|
if (material.HasProperty(sheenColorTexture))
|
|
cc.sheenColorTexture = exporter.ExportTextureInfoWithTextureTransform(material, material.GetTexture(sheenColorTexture), nameof(sheenColorTexture));
|
|
|
|
if (material.HasProperty(sheenRoughnessFactor))
|
|
cc.sheenRoughnessFactor = material.GetFloat(sheenRoughnessFactor);
|
|
if (material.HasProperty(sheenRoughnessTexture))
|
|
cc.sheenRoughnessTexture = exporter.ExportTextureInfoWithTextureTransform(material, material.GetTexture(sheenRoughnessTexture), nameof(sheenRoughnessTexture));
|
|
}
|
|
}
|
|
}
|
|
}
|