added KHR_materials_ior and KHR_materials_specular GLTF extension support

This commit is contained in:
Turanszki Janos
2021-05-29 17:41:30 +02:00
parent 1ee087f4b8
commit d26a31d3bb
15 changed files with 193 additions and 45 deletions
+6 -2
View File
@@ -11,7 +11,7 @@ using namespace wiScene;
void MaterialWindow::Create(EditorComponent* editor)
{
wiWindow::Create("Material Window");
SetSize(XMFLOAT2(720, 600));
SetSize(XMFLOAT2(720, 620));
float x = 670, y = 0;
float hei = 18;
@@ -220,7 +220,7 @@ void MaterialWindow::Create(EditorComponent* editor)
AddWidget(&roughnessSlider);
reflectanceSlider.Create(0, 1, 0.5f, 1000, "Reflectance: ");
reflectanceSlider.SetTooltip("Adjust the overall surface reflectivity.\nNote: this is not available in specular-glossiness workflow");
reflectanceSlider.SetTooltip("Adjust the surface [non-metal] reflectivity (also called specularFactor).\nNote: this is not available in specular-glossiness workflow");
reflectanceSlider.SetSize(XMFLOAT2(wid, hei));
reflectanceSlider.SetPos(XMFLOAT2(x, y += step));
reflectanceSlider.OnSlide([&](wiEventArgs args) {
@@ -581,6 +581,10 @@ void MaterialWindow::Create(EditorComponent* editor)
slots[i].label.SetText("ClearcoatNormMap:");
slots[i].button.SetTooltip("RGB: Normal");
break;
case MaterialComponent::SPECULARMAP:
slots[i].label.SetText("SpecularMap:");
slots[i].button.SetTooltip("RGB: Specular color, A: Specular intensity [non-metal]");
break;
default:
break;
}
+83 -1
View File
@@ -321,7 +321,7 @@ void ImportModel_GLTF(const std::string& fileName, Scene& scene)
material.baseColor = XMFLOAT4(1, 1, 1, 1);
material.roughness = 1.0f;
material.metalness = 1.0f;
material.reflectance = 0.02f;
material.reflectance = 0.04f;
material.SetDoubleSided(x.doubleSided);
@@ -420,12 +420,16 @@ void ImportModel_GLTF(const std::string& fileName, Scene& scene)
auto ext_unlit = x.extensions.find("KHR_materials_unlit");
if (ext_unlit != x.extensions.end())
{
// https://github.com/KhronosGroup/glTF/tree/master/extensions/2.0/Khronos/KHR_materials_unlit
material.shaderType = MaterialComponent::SHADERTYPE_UNLIT;
}
auto ext_transmission = x.extensions.find("KHR_materials_transmission");
if (ext_transmission != x.extensions.end())
{
// https://github.com/KhronosGroup/glTF/tree/master/extensions/2.0/Khronos/KHR_materials_transmission
if (ext_transmission->second.Has("transmissionFactor"))
{
auto& factor = ext_transmission->second.Get("transmissionFactor");
@@ -446,6 +450,8 @@ void ImportModel_GLTF(const std::string& fileName, Scene& scene)
auto specularGlossinessWorkflow = x.extensions.find("KHR_materials_pbrSpecularGlossiness");
if (specularGlossinessWorkflow != x.extensions.end())
{
// https://github.com/KhronosGroup/glTF/tree/master/extensions/2.0/Khronos/KHR_materials_pbrSpecularGlossiness
material.SetUseSpecularGlossinessWorkflow(true);
if (specularGlossinessWorkflow->second.Has("diffuseTexture"))
@@ -493,6 +499,8 @@ void ImportModel_GLTF(const std::string& fileName, Scene& scene)
auto ext_sheen = x.extensions.find("KHR_materials_sheen");
if (ext_sheen != x.extensions.end())
{
// https://github.com/KhronosGroup/glTF/tree/master/extensions/2.0/Khronos/KHR_materials_sheen
material.shaderType = MaterialComponent::SHADERTYPE_PBR_CLOTH;
if (ext_sheen->second.Has("sheenColorFactor"))
@@ -533,6 +541,8 @@ void ImportModel_GLTF(const std::string& fileName, Scene& scene)
auto ext_clearcoat = x.extensions.find("KHR_materials_clearcoat");
if (ext_clearcoat != x.extensions.end())
{
// https://github.com/KhronosGroup/glTF/tree/master/extensions/2.0/Khronos/KHR_materials_clearcoat
if (material.shaderType == MaterialComponent::SHADERTYPE_PBR_CLOTH)
{
material.shaderType = MaterialComponent::SHADERTYPE_PBR_CLOTH_CLEARCOAT;
@@ -584,6 +594,78 @@ void ImportModel_GLTF(const std::string& fileName, Scene& scene)
}
}
auto ext_ior = x.extensions.find("KHR_materials_ior");
if (ext_ior != x.extensions.end())
{
// https://github.com/KhronosGroup/glTF/tree/master/extensions/2.0/Khronos/KHR_materials_ior
if (ext_ior->second.Has("ior"))
{
auto& factor = ext_ior->second.Get("ior");
float ior = float(factor.IsNumber() ? factor.Get<double>() : factor.Get<int>());
material.reflectance = std::pow((ior - 1.0f) / (ior + 1.0f), 2.0f);
}
}
auto ext_specular = x.extensions.find("KHR_materials_specular");
if (ext_specular != x.extensions.end())
{
// https://github.com/KhronosGroup/glTF/tree/master/extensions/2.0/Khronos/KHR_materials_specular
material.specularColor = XMFLOAT4(1, 1, 1, 1);
if (ext_specular->second.Has("specularFactor"))
{
auto& factor = ext_specular->second.Get("specularFactor");
material.specularColor.w = float(factor.IsNumber() ? factor.Get<double>() : factor.Get<int>());
}
if (ext_specular->second.Has("specularTexture"))
{
if (material.textures[MaterialComponent::SURFACEMAP].resource == nullptr)
{
auto& param = ext_specular->second.Get("specularTexture");
int index = param.Get("index").Get<int>();
auto& tex = state.gltfModel.textures[index];
auto& img = state.gltfModel.images[tex.source];
material.textures[MaterialComponent::SURFACEMAP].resource = wiResourceManager::Load(img.uri);
material.textures[MaterialComponent::SURFACEMAP].name = img.uri;
material.textures[MaterialComponent::SURFACEMAP].uvset = (uint32_t)param.Get("texCoord").Get<int>();
}
else if (material.textures[MaterialComponent::SPECULARMAP].resource == nullptr)
{
auto& param = ext_specular->second.Get("specularTexture");
int index = param.Get("index").Get<int>();
auto& tex = state.gltfModel.textures[index];
auto& img = state.gltfModel.images[tex.source];
material.textures[MaterialComponent::SPECULARMAP].resource = wiResourceManager::Load(img.uri);
material.textures[MaterialComponent::SPECULARMAP].name = img.uri;
material.textures[MaterialComponent::SPECULARMAP].uvset = (uint32_t)param.Get("texCoord").Get<int>();
}
else
{
wiBackLog::post("[KHR_materials_specular warning] specularTexture must be either in surfaceMap.a or specularColorTexture.a! specularTexture discarded!");
}
}
if (ext_specular->second.Has("specularColorTexture"))
{
auto& param = ext_specular->second.Get("specularColorTexture");
int index = param.Get("index").Get<int>();
auto& tex = state.gltfModel.textures[index];
auto& img = state.gltfModel.images[tex.source];
material.textures[MaterialComponent::SPECULARMAP].resource = wiResourceManager::Load(img.uri);
material.textures[MaterialComponent::SPECULARMAP].name = img.uri;
material.textures[MaterialComponent::SPECULARMAP].uvset = (uint32_t)param.Get("texCoord").Get<int>();
}
if (ext_specular->second.Has("specularColorFactor"))
{
auto& factor = ext_specular->second.Get("specularColorFactor");
material.specularColor.x = factor.ArrayLen() > 0 ? float(factor.Get(0).IsNumber() ? factor.Get(0).Get<double>() : factor.Get(0).Get<int>()) : 1.0f;
material.specularColor.y = factor.ArrayLen() > 0 ? float(factor.Get(1).IsNumber() ? factor.Get(1).Get<double>() : factor.Get(1).Get<int>()) : 1.0f;
material.specularColor.z = factor.ArrayLen() > 0 ? float(factor.Get(2).IsNumber() ? factor.Get(2).Get<double>() : factor.Get(2).Get<int>()) : 1.0f;
}
}
}
if (scene.materials.GetCount() == 0)
+1
View File
@@ -1,5 +1,6 @@
This file contains changelog of wiArchive versions
68: serialized MaterialComponent SPECULARMAP (for KHR_materials_specular)
67: ocean water color float3 -> float4 (alpha in effect now)
66: serialized WeatherComponent::atmosphereParameters and skyExposure
65: serialized CameraComponent focal_length, aperture_size and aperture_shape
+23 -21
View File
@@ -74,11 +74,12 @@
#define TEXSLOT_ONDEMAND28 58
#define TEXSLOT_ONDEMAND29 59
#define TEXSLOT_ONDEMAND30 60
#define TEXSLOT_ONDEMAND31 61
#define TEXSLOT_ONDEMAND_COUNT (TEXSLOT_ONDEMAND30 - TEXSLOT_ONDEMAND0 + 1)
// These are reserved for demand of any type of textures in specific shaders:
#define TEXSLOT_UNIQUE0 61
#define TEXSLOT_UNIQUE1 62
#define TEXSLOT_UNIQUE0 62
#define TEXSLOT_UNIQUE1 63
#define TEXSLOT_COUNT 64
@@ -102,30 +103,31 @@
#define TEXSLOT_RENDERER_CLEARCOATMAP TEXSLOT_ONDEMAND9
#define TEXSLOT_RENDERER_CLEARCOATROUGHNESSMAP TEXSLOT_ONDEMAND10
#define TEXSLOT_RENDERER_CLEARCOATNORMALMAP TEXSLOT_ONDEMAND11
#define TEXSLOT_RENDERER_SPECULARMAP TEXSLOT_ONDEMAND12
#define TEXSLOT_RENDERER_BLEND1_BASECOLORMAP TEXSLOT_ONDEMAND19
#define TEXSLOT_RENDERER_BLEND1_NORMALMAP TEXSLOT_ONDEMAND20
#define TEXSLOT_RENDERER_BLEND1_SURFACEMAP TEXSLOT_ONDEMAND21
#define TEXSLOT_RENDERER_BLEND1_EMISSIVEMAP TEXSLOT_ONDEMAND22
#define TEXSLOT_RENDERER_BLEND1_BASECOLORMAP TEXSLOT_ONDEMAND20
#define TEXSLOT_RENDERER_BLEND1_NORMALMAP TEXSLOT_ONDEMAND21
#define TEXSLOT_RENDERER_BLEND1_SURFACEMAP TEXSLOT_ONDEMAND22
#define TEXSLOT_RENDERER_BLEND1_EMISSIVEMAP TEXSLOT_ONDEMAND23
#define TEXSLOT_RENDERER_BLEND2_BASECOLORMAP TEXSLOT_ONDEMAND23
#define TEXSLOT_RENDERER_BLEND2_NORMALMAP TEXSLOT_ONDEMAND24
#define TEXSLOT_RENDERER_BLEND2_SURFACEMAP TEXSLOT_ONDEMAND25
#define TEXSLOT_RENDERER_BLEND2_EMISSIVEMAP TEXSLOT_ONDEMAND26
#define TEXSLOT_RENDERER_BLEND2_BASECOLORMAP TEXSLOT_ONDEMAND24
#define TEXSLOT_RENDERER_BLEND2_NORMALMAP TEXSLOT_ONDEMAND25
#define TEXSLOT_RENDERER_BLEND2_SURFACEMAP TEXSLOT_ONDEMAND26
#define TEXSLOT_RENDERER_BLEND2_EMISSIVEMAP TEXSLOT_ONDEMAND27
#define TEXSLOT_RENDERER_BLEND3_BASECOLORMAP TEXSLOT_ONDEMAND27
#define TEXSLOT_RENDERER_BLEND3_NORMALMAP TEXSLOT_ONDEMAND28
#define TEXSLOT_RENDERER_BLEND3_SURFACEMAP TEXSLOT_ONDEMAND29
#define TEXSLOT_RENDERER_BLEND3_EMISSIVEMAP TEXSLOT_ONDEMAND30
#define TEXSLOT_RENDERER_BLEND3_BASECOLORMAP TEXSLOT_ONDEMAND28
#define TEXSLOT_RENDERER_BLEND3_NORMALMAP TEXSLOT_ONDEMAND29
#define TEXSLOT_RENDERER_BLEND3_SURFACEMAP TEXSLOT_ONDEMAND30
#define TEXSLOT_RENDERER_BLEND3_EMISSIVEMAP TEXSLOT_ONDEMAND31
// RenderPath texture mappings:
#define TEXSLOT_RENDERPATH_ENTITYTILES TEXSLOT_ONDEMAND12
#define TEXSLOT_RENDERPATH_REFLECTION TEXSLOT_ONDEMAND13
#define TEXSLOT_RENDERPATH_REFRACTION TEXSLOT_ONDEMAND14
#define TEXSLOT_RENDERPATH_WATERRIPPLES TEXSLOT_ONDEMAND15
#define TEXSLOT_RENDERPATH_AO TEXSLOT_ONDEMAND16
#define TEXSLOT_RENDERPATH_SSR TEXSLOT_ONDEMAND17
#define TEXSLOT_RENDERPATH_RTSHADOW TEXSLOT_ONDEMAND18
#define TEXSLOT_RENDERPATH_ENTITYTILES TEXSLOT_ONDEMAND13
#define TEXSLOT_RENDERPATH_REFLECTION TEXSLOT_ONDEMAND14
#define TEXSLOT_RENDERPATH_REFRACTION TEXSLOT_ONDEMAND15
#define TEXSLOT_RENDERPATH_WATERRIPPLES TEXSLOT_ONDEMAND16
#define TEXSLOT_RENDERPATH_AO TEXSLOT_ONDEMAND17
#define TEXSLOT_RENDERPATH_SSR TEXSLOT_ONDEMAND18
#define TEXSLOT_RENDERPATH_RTSHADOW TEXSLOT_ONDEMAND19
// wiImage:
#define TEXSLOT_IMAGE_BASE TEXSLOT_ONDEMAND0
+15 -4
View File
@@ -30,6 +30,11 @@ struct ShaderMaterial
float alphaTest;
float displacementMapping;
float transmission;
uint options;
int padding0;
int padding1;
uint layerMask;
int uvset_baseColorMap;
int uvset_surfaceMap;
@@ -40,19 +45,20 @@ struct ShaderMaterial
int uvset_occlusionMap;
int uvset_transmissionMap;
float2 padding1;
float transmission;
uint options;
int uvset_sheenColorMap;
int uvset_sheenRoughnessMap;
int uvset_clearcoatMap;
int uvset_clearcoatRoughnessMap;
int uvset_clearcoatNormalMap;
int uvset_specularMap;
int padding2;
int padding3;
float sheenRoughness;
float clearcoat;
float clearcoatRoughness;
float padding4;
float4 sheenColor;
@@ -76,6 +82,11 @@ struct ShaderMaterial
int texture_clearcoatroughnessmap_index;
int texture_clearcoatnormalmap_index;
int texture_specularmap_index;
int padding5;
int padding6;
int padding7;
inline bool IsUsingVertexColors() { return options & SHADERMATERIAL_OPTION_BIT_USE_VERTEXCOLORS; }
inline bool IsUsingSpecularGlossinessWorkflow() { return options & SHADERMATERIAL_OPTION_BIT_SPECULARGLOSSINESS_WORKFLOW; }
inline bool IsOcclusionEnabled_Primary() { return options & SHADERMATERIAL_OPTION_BIT_OCCLUSION_PRIMARY; }
+14 -2
View File
@@ -87,6 +87,17 @@ float3 F_Schlick(const float3 f0, float f90, float VoH)
return f0 + (f90 - f0) * pow5(1.0 - VoH);
}
float iorToF0(float transmittedIor, float incidentIor)
{
return sqr((transmittedIor - incidentIor) / (transmittedIor + incidentIor));
}
float f0ToIor(float f0)
{
float r = sqrt(f0);
return (1.0 + r) / (1.0 - r);
}
// Surface descriptors:
@@ -185,14 +196,15 @@ struct Surface
inline void create(
in ShaderMaterial material,
in float4 baseColor,
in float4 surfaceMap
in float4 surfaceMap,
in float4 specularMap = 1
)
{
init();
opacity = baseColor.a;
roughness = material.roughness;
f0 = material.specularColor.rgb * material.specularColor.a;
f0 = material.specularColor.rgb * specularMap.rgb * specularMap.a * material.specularColor.a;
[branch]
if (material.IsUsingSpecularGlossinessWorkflow())
+17 -1
View File
@@ -65,6 +65,7 @@ inline ShaderMaterial GetMaterial3()
#define texture_clearcoatmap bindless_textures[GetMaterial().texture_clearcoatmap_index]
#define texture_clearcoatroughnessmap bindless_textures[GetMaterial().texture_clearcoatroughnessmap_index]
#define texture_clearcoatnormalmap bindless_textures[GetMaterial().texture_clearcoatnormalmap_index]
#define texture_specularmap bindless_textures[GetMaterial().texture_specularmap_index]
#define texture_blend1_basecolormap bindless_textures[GetMaterial1().texture_basecolormap_index]
#define texture_blend1_normalmap bindless_textures[GetMaterial1().texture_normalmap_index]
@@ -114,6 +115,7 @@ TEXTURE2D(texture_sheenroughnessmap, float4, TEXSLOT_RENDERER_SHEENROUGHNESSMAP)
TEXTURE2D(texture_clearcoatmap, float, TEXSLOT_RENDERER_CLEARCOATMAP); // r
TEXTURE2D(texture_clearcoatroughnessmap, float2, TEXSLOT_RENDERER_CLEARCOATROUGHNESSMAP); // g
TEXTURE2D(texture_clearcoatnormalmap, float3, TEXSLOT_RENDERER_CLEARCOATNORMALMAP); // rgb
TEXTURE2D(texture_specularmap, float4, TEXSLOT_RENDERER_SPECULARMAP); // rgb color, a intensity
TEXTURE2D(texture_blend1_basecolormap, float4, TEXSLOT_RENDERER_BLEND1_BASECOLORMAP); // rgb: baseColor, a: opacity
TEXTURE2D(texture_blend1_normalmap, float3, TEXSLOT_RENDERER_BLEND1_NORMALMAP); // rgb: normal
@@ -1392,7 +1394,21 @@ float4 main(PixelInput input, in bool is_frontface : SV_IsFrontFace) : SV_TARGET
#endif // OBJECTSHADER_USE_UVSETS
surface.create(GetMaterial(), color, surfaceMap);
float4 specularMap = 1;
#ifdef OBJECTSHADER_USE_UVSETS
[branch]
if (GetMaterial().uvset_specularMap >= 0)
{
const float2 UV_specularMap = GetMaterial().uvset_specularMap == 0 ? input.uvsets.xy : input.uvsets.zw;
specularMap = texture_specularmap.Sample(sampler_objectshader, UV_specularMap);
specularMap.rgb = DEGAMMA(specularMap.rgb);
}
#endif // OBJECTSHADER_USE_UVSETS
surface.create(GetMaterial(), color, surfaceMap, specularMap);
// Emissive map:
+3 -3
View File
@@ -285,7 +285,7 @@ void main(uint3 DTid : SV_DispatchThreadID, uint groupIndex : SV_GroupIndex)
{
lighting.direct.specular = lightColor * BRDF_GetSpecular(surface, surfaceToLight);
lighting.direct.diffuse = lightColor * BRDF_GetDiffuse(surface, surfaceToLight);
result += max(0, shadow * (surface.albedo * lighting.direct.diffuse + lighting.direct.specular)) * surface.opacity;
result += max(0, shadow * (surface.albedo * (1 - surface.transmission) * lighting.direct.diffuse + lighting.direct.specular)) * surface.opacity;
}
}
}
@@ -314,7 +314,7 @@ void main(uint3 DTid : SV_DispatchThreadID, uint groupIndex : SV_GroupIndex)
{
const float refractChance = surface.transmission;
roulette = rand(seed, uv);
if (roulette < refractChance)
if (roulette <= refractChance)
{
// Refraction
const float3 R = refract(ray.Direction, surface.N, 1 - material.refraction);
@@ -329,7 +329,7 @@ void main(uint3 DTid : SV_DispatchThreadID, uint groupIndex : SV_GroupIndex)
const float specChance = dot(surface.F, 0.333);
roulette = rand(seed, uv);
if (roulette < specChance)
if (roulette <= specChance)
{
// Specular reflection
const float3 R = reflect(ray.Direction, surface.N);
+10 -1
View File
@@ -117,7 +117,16 @@ void EvaluateObjectSurface(
surfaceMap = bindless_textures[NonUniformResourceIndex(material.texture_surfacemap_index)].SampleLevel(sampler_linear_wrap, UV_surfaceMap, 0);
}
surface.create(material, baseColor, surfaceMap);
float4 specularMap = 1;
[branch]
if (material.texture_specularmap_index >= 0)
{
const float2 UV_specularMap = material.uvset_specularMap == 0 ? uvsets.xy : uvsets.zw;
specularMap = bindless_textures[NonUniformResourceIndex(material.texture_specularmap_index)].SampleLevel(sampler_linear_wrap, UV_specularMap, 0);
specularMap.rgb = DEGAMMA(specularMap.rgb);
}
surface.create(material, baseColor, surfaceMap, specularMap);
surface.emissiveColor = material.emissiveColor;
[branch]
+1 -1
View File
@@ -4,7 +4,7 @@
#include <fstream>
// this should always be only INCREMENTED and only if a new serialization is implemeted somewhere!
uint64_t __archiveVersion = 67;
uint64_t __archiveVersion = 68;
// this is the version number of which below the archive is not compatible with the current version
uint64_t __archiveVersionBarrier = 22;
+2
View File
@@ -258,6 +258,7 @@ namespace wiScene
dest->uvset_clearcoatMap = textures[CLEARCOATMAP].GetUVSet();
dest->uvset_clearcoatRoughnessMap = textures[CLEARCOATROUGHNESSMAP].GetUVSet();
dest->uvset_clearcoatNormalMap = textures[CLEARCOATNORMALMAP].GetUVSet();
dest->uvset_specularMap = textures[SPECULARMAP].GetUVSet();
dest->sheenColor = sheenColor;
dest->sheenRoughness = sheenRoughness;
dest->clearcoat = clearcoat;
@@ -308,6 +309,7 @@ namespace wiScene
dest->texture_clearcoatmap_index = device->GetDescriptorIndex(textures[CLEARCOATMAP].GetGPUResource(), SRV);
dest->texture_clearcoatroughnessmap_index = device->GetDescriptorIndex(textures[CLEARCOATROUGHNESSMAP].GetGPUResource(), SRV);
dest->texture_clearcoatnormalmap_index = device->GetDescriptorIndex(textures[CLEARCOATNORMALMAP].GetGPUResource(), SRV);
dest->texture_specularmap_index = device->GetDescriptorIndex(textures[SPECULARMAP].GetGPUResource(), SRV);
dest->baseColorAtlasMulAdd = XMFLOAT4(0, 0, 0, 0);
dest->surfaceMapAtlasMulAdd = XMFLOAT4(0, 0, 0, 0);
+1
View File
@@ -196,6 +196,7 @@ namespace wiScene
CLEARCOATMAP,
CLEARCOATROUGHNESSMAP,
CLEARCOATNORMALMAP,
SPECULARMAP,
TEXTURESLOT_COUNT
};
+12
View File
@@ -209,6 +209,12 @@ namespace wiScene
archive >> textures[CLEARCOATNORMALMAP].uvset;
}
if (archive.GetVersion() >= 68)
{
archive >> textures[SPECULARMAP].name;
archive >> textures[SPECULARMAP].uvset;
}
for (auto& x : textures)
{
if (!x.name.empty())
@@ -328,6 +334,12 @@ namespace wiScene
archive << textures[CLEARCOATROUGHNESSMAP].uvset;
archive << textures[CLEARCOATNORMALMAP].uvset;
}
if (archive.GetVersion() >= 68)
{
archive << textures[SPECULARMAP].name;
archive << textures[SPECULARMAP].uvset;
}
}
}
void MeshComponent::Serialize(wiArchive& archive, EntitySerializer& seri)
+1 -1
View File
@@ -9,7 +9,7 @@ namespace wiVersion
// minor features, major updates, breaking compatibility changes
const int minor = 56;
// minor bug fixes, alterations, refactors, updates
const int revision = 24;
const int revision = 25;
const std::string version_string = std::to_string(major) + "." + std::to_string(minor) + "." + std::to_string(revision);
+4 -8
View File
@@ -7,11 +7,10 @@ Vulkan renderer
Image rendering
Font rendering (True Type)
Networking (UDP)
[removed since 0.21] Blender-exporter: 3D meshes,objects,armatures,animation,materials,lights,hitspheres,wind,world info,dynamic cameras,ribbon trails,particle systems
3D mesh rendering
Skeletal animation
Morph target animation
Physically based materials
Physically based rendering
Animated texturing
Normal mapping
Displacement mapping
@@ -20,7 +19,6 @@ Real time planar reflections
Cube map reflections (static and real time)
Refractions (screen space, blurred)
Interactive Water
Gaussian Blur
Bloom
Edge outline
Motion Blur
@@ -38,7 +36,6 @@ MSAA (Forward rendering only)
FXAA
TAA (Temporal Antialiasing)
Supersampling
Deferred shading
Directional lights + cascaded shadow maps
Spotlights + shadow maps
Point lights + shadow cubemaps
@@ -54,7 +51,6 @@ Screen Space Ambient Occlusion (SSAO, HBAO, MSAO)
Screen Space Reflections
Skin shader (Subsurface scattering)
Stencil layering
Deferred decals
Forward decals
Color Grading
Sharpen filter
@@ -63,14 +59,12 @@ Lua Scripting
Dynamic environment mapping
Impostor system
Tiled forward (Forward+) rendering (+2.5D culling)
Tiled deferred rendering
Occlusion culling with gpu queries
Texture atlas packing
Tiled decals
Area lights: Sphere, Disc, Rectangle, Tube
Frame Profiler
Voxel Global Illumination
Huge draw distance support with reversed Z-buffer
Reversed Z-buffer
Force Fields GPU simulation
Particle - Depth Buffer collisions
Ocean simulation (FFT)
@@ -96,3 +90,5 @@ KHR_materials_transmission
KHR_materials_pbrSpecularGlossiness
KHR_materials_sheen
KHR_materials_clearcoat
KHR_materials_specular
KHR_materials_ior