mirror of
https://github.com/vrm-c/UniVRM.git
synced 2026-08-20 01:25:45 -05:00
Merge pull request #780 from ousttrue/fix/roughness_smooth_conversion
MetallicRoughnessOcclusion テクスチャーの取り廻しを中心に改修
This commit is contained in:
@@ -8,10 +8,7 @@ namespace UniGLTF
|
||||
public static Task<Texture2D> LoadTaskAsync(UnityPath m_assetPath,
|
||||
glTF gltf, int textureIndex)
|
||||
{
|
||||
var textureType = TextureIO.GetglTFTextureType(gltf, textureIndex);
|
||||
var colorSpace = TextureIO.GetColorSpace(textureType);
|
||||
var isLinear = colorSpace == RenderTextureReadWrite.Linear;
|
||||
var sampler = gltf.GetSamplerFromTextureIndex(textureIndex);
|
||||
var colorSpace = gltf.GetColorSpace(textureIndex);
|
||||
|
||||
//
|
||||
// texture from assets
|
||||
@@ -25,7 +22,7 @@ namespace UniGLTF
|
||||
else
|
||||
{
|
||||
importer.maxTextureSize = 8192;
|
||||
importer.sRGBTexture = !isLinear;
|
||||
importer.sRGBTexture = colorSpace == RenderTextureReadWrite.sRGB;
|
||||
importer.SaveAndReimport();
|
||||
}
|
||||
|
||||
@@ -50,6 +47,7 @@ namespace UniGLTF
|
||||
importer.SaveAndReimport();
|
||||
}
|
||||
|
||||
var sampler = gltf.GetSamplerFromTextureIndex(textureIndex);
|
||||
if (sampler != null)
|
||||
{
|
||||
TextureSamplerUtil.SetSampler(Texture, sampler);
|
||||
|
||||
@@ -30,8 +30,8 @@ namespace UniGLTF
|
||||
}
|
||||
}
|
||||
|
||||
static bool s_foldMaterials;
|
||||
static bool s_foldTextures;
|
||||
static bool s_foldMaterials = true;
|
||||
static bool s_foldTextures = true;
|
||||
|
||||
public static void OnGUIMaterial(ScriptedImporter importer, GltfParser parser)
|
||||
{
|
||||
@@ -56,7 +56,17 @@ namespace UniGLTF
|
||||
s_foldTextures = EditorGUILayout.Foldout(s_foldTextures, "Remapped Textures");
|
||||
if (s_foldTextures)
|
||||
{
|
||||
DrawRemapGUI<UnityEngine.Texture2D>(importer, GltfTextureEnumerator.Enumerate(parser.GLTF).Select(x => x.ConvertedName));
|
||||
DrawRemapGUI<UnityEngine.Texture2D>(importer, GltfTextureEnumerator.Enumerate(parser.GLTF).Select(x =>
|
||||
{
|
||||
switch (x.TextureType)
|
||||
{
|
||||
case GetTextureParam.TextureTypes.NormalMap:
|
||||
return x.GltflName;
|
||||
|
||||
default:
|
||||
return x.ConvertedName;
|
||||
}
|
||||
}));
|
||||
}
|
||||
|
||||
if (GUILayout.Button("Clear"))
|
||||
|
||||
@@ -17,14 +17,7 @@ namespace UniGLTF
|
||||
|
||||
public override void OnImportAsset(AssetImportContext ctx)
|
||||
{
|
||||
try
|
||||
{
|
||||
ScriptedImporterImpl.Import(this, ctx, m_reverseAxis);
|
||||
}
|
||||
catch (System.Exception ex)
|
||||
{
|
||||
Debug.LogError(ex);
|
||||
}
|
||||
ScriptedImporterImpl.Import(this, ctx, m_reverseAxis);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -17,14 +17,7 @@ namespace UniGLTF
|
||||
|
||||
public override void OnImportAsset(AssetImportContext ctx)
|
||||
{
|
||||
try
|
||||
{
|
||||
ScriptedImporterImpl.Import(this, ctx, m_reverseAxis);
|
||||
}
|
||||
catch (System.Exception ex)
|
||||
{
|
||||
Debug.LogError(ex);
|
||||
}
|
||||
ScriptedImporterImpl.Import(this, ctx, m_reverseAxis);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using UnityEditor;
|
||||
@@ -40,6 +41,12 @@ namespace UniGLTF
|
||||
externalObjectMap.Where(x => x.Value != null).Select(x => (x.Value.name, x.Value)).Concat(
|
||||
EnumerateTexturesFromUri(externalObjectMap, parser, UnityPath.FromUnityPath(scriptedImporter.assetPath).Parent))))
|
||||
{
|
||||
// settings TextureImporters
|
||||
foreach (var textureInfo in GltfTextureEnumerator.Enumerate(parser.GLTF))
|
||||
{
|
||||
TextureImporterConfigurator.Configure(textureInfo, loaded.TextureFactory.ExternalMap);
|
||||
}
|
||||
|
||||
loaded.InvertAxis = reverseAxis;
|
||||
loaded.Load();
|
||||
loaded.ShowMeshes();
|
||||
@@ -69,8 +76,7 @@ namespace UniGLTF
|
||||
{
|
||||
switch (texParam.TextureType)
|
||||
{
|
||||
case GetTextureParam.METALLIC_GLOSS_PROP:
|
||||
case GetTextureParam.OCCLUSION_PROP:
|
||||
case GetTextureParam.TextureTypes.StandardMap:
|
||||
break;
|
||||
|
||||
default:
|
||||
|
||||
@@ -70,8 +70,7 @@ namespace UniGLTF
|
||||
|
||||
switch (param.TextureType)
|
||||
{
|
||||
case GetTextureParam.METALLIC_GLOSS_PROP:
|
||||
case GetTextureParam.OCCLUSION_PROP:
|
||||
case GetTextureParam.TextureTypes.StandardMap:
|
||||
{
|
||||
// write converted texture
|
||||
targetPath = $"{m_path}/{param.ConvertedName}.png";
|
||||
@@ -130,40 +129,13 @@ namespace UniGLTF
|
||||
|
||||
EditorApplication.delayCall += () =>
|
||||
{
|
||||
// Wait for the texture assets to be imported
|
||||
|
||||
foreach (var kv in extractor.Textures)
|
||||
{
|
||||
var targetPath = kv.Key;
|
||||
var param = kv.Value;
|
||||
|
||||
// TextureImporter
|
||||
var targetTextureImporter = AssetImporter.GetAtPath(targetPath) as TextureImporter;
|
||||
if (targetTextureImporter != null)
|
||||
{
|
||||
switch (param.TextureType)
|
||||
{
|
||||
case GetTextureParam.OCCLUSION_PROP:
|
||||
case GetTextureParam.METALLIC_GLOSS_PROP:
|
||||
#if VRM_DEVELOP
|
||||
Debug.Log($"{targetPath} => linear");
|
||||
#endif
|
||||
targetTextureImporter.sRGBTexture = false;
|
||||
targetTextureImporter.SaveAndReimport();
|
||||
break;
|
||||
|
||||
case GetTextureParam.NORMAL_PROP:
|
||||
#if VRM_DEVELOP
|
||||
Debug.Log($"{targetPath} => normalmap");
|
||||
#endif
|
||||
targetTextureImporter.textureType = TextureImporterType.NormalMap;
|
||||
targetTextureImporter.SaveAndReimport();
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new FileNotFoundException(targetPath);
|
||||
}
|
||||
|
||||
// remap
|
||||
var externalObject = AssetDatabase.LoadAssetAtPath<UnityEngine.Texture2D>(targetPath);
|
||||
if (externalObject != null)
|
||||
|
||||
74
Assets/UniGLTF/Editor/UniGLTF/TextureImporterConfigurator.cs
Normal file
74
Assets/UniGLTF/Editor/UniGLTF/TextureImporterConfigurator.cs
Normal file
@@ -0,0 +1,74 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using UnityEditor;
|
||||
using UnityEngine;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public static class TextureImporterConfigurator
|
||||
{
|
||||
public static void ConfigureNormalMap(Texture2D texture)
|
||||
{
|
||||
var path = UnityPath.FromAsset(texture);
|
||||
if (AssetImporter.GetAtPath(path.Value) is TextureImporter textureImporter)
|
||||
{
|
||||
#if VRM_DEVELOP
|
||||
Debug.Log($"{path} => normalmap");
|
||||
#endif
|
||||
textureImporter.textureType = TextureImporterType.NormalMap;
|
||||
textureImporter.SaveAndReimport();
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new System.IO.FileNotFoundException($"{path}");
|
||||
}
|
||||
}
|
||||
|
||||
public static void ConfigureLinear(Texture2D texture)
|
||||
{
|
||||
var path = UnityPath.FromAsset(texture);
|
||||
if (AssetImporter.GetAtPath(path.Value) is TextureImporter textureImporter)
|
||||
{
|
||||
#if VRM_DEVELOP
|
||||
Debug.Log($"{path} => linear");
|
||||
#endif
|
||||
textureImporter.sRGBTexture = false;
|
||||
textureImporter.SaveAndReimport();
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new System.IO.FileNotFoundException($"{path}");
|
||||
}
|
||||
}
|
||||
|
||||
public static void Configure(GetTextureParam textureInfo, IDictionary<string, Texture2D> ExternalMap)
|
||||
{
|
||||
switch (textureInfo.TextureType)
|
||||
{
|
||||
case GetTextureParam.TextureTypes.NormalMap:
|
||||
{
|
||||
if (ExternalMap.TryGetValue(textureInfo.GltflName, out Texture2D external))
|
||||
{
|
||||
ConfigureNormalMap(external);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case GetTextureParam.TextureTypes.StandardMap:
|
||||
{
|
||||
if (ExternalMap.TryGetValue(textureInfo.ConvertedName, out Texture2D external))
|
||||
{
|
||||
ConfigureLinear(external);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case GetTextureParam.TextureTypes.sRGB:
|
||||
break;
|
||||
|
||||
default:
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,5 +1,5 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 55c6531d46a98a845b19cbe1f938eab1
|
||||
guid: 193b7c6393807a04f8aafabc23478f8e
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
@@ -5,12 +5,10 @@ namespace UniGLTF
|
||||
{
|
||||
public enum glTFTextureTypes
|
||||
{
|
||||
BaseColor,
|
||||
Metallic,
|
||||
OcclusionMetallicRoughness,
|
||||
Normal,
|
||||
Occlusion,
|
||||
Emissive,
|
||||
Unknown
|
||||
SRGB,
|
||||
Linear,
|
||||
}
|
||||
|
||||
public interface IglTFTextureinfo
|
||||
@@ -38,19 +36,13 @@ namespace UniGLTF
|
||||
[Serializable]
|
||||
public class glTFMaterialBaseColorTextureInfo : glTFTextureInfo
|
||||
{
|
||||
public override glTFTextureTypes TextureType
|
||||
{
|
||||
get { return glTFTextureTypes.BaseColor; }
|
||||
}
|
||||
public override glTFTextureTypes TextureType => glTFTextureTypes.SRGB;
|
||||
}
|
||||
|
||||
[Serializable]
|
||||
public class glTFMaterialMetallicRoughnessTextureInfo : glTFTextureInfo
|
||||
{
|
||||
public override glTFTextureTypes TextureType
|
||||
{
|
||||
get { return glTFTextureTypes.Metallic; }
|
||||
}
|
||||
public override glTFTextureTypes TextureType => glTFTextureTypes.OcclusionMetallicRoughness;
|
||||
}
|
||||
|
||||
[Serializable]
|
||||
@@ -70,19 +62,13 @@ namespace UniGLTF
|
||||
[JsonSchema(Minimum = 0.0, Maximum = 1.0)]
|
||||
public float strength = 1.0f;
|
||||
|
||||
public override glTFTextureTypes TextureType
|
||||
{
|
||||
get { return glTFTextureTypes.Occlusion; }
|
||||
}
|
||||
public override glTFTextureTypes TextureType => glTFTextureTypes.OcclusionMetallicRoughness;
|
||||
}
|
||||
|
||||
[Serializable]
|
||||
public class glTFMaterialEmissiveTextureInfo : glTFTextureInfo
|
||||
{
|
||||
public override glTFTextureTypes TextureType
|
||||
{
|
||||
get { return glTFTextureTypes.Emissive; }
|
||||
}
|
||||
public override glTFTextureTypes TextureType => glTFTextureTypes.SRGB;
|
||||
}
|
||||
|
||||
[Serializable]
|
||||
|
||||
@@ -1,16 +0,0 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using UnityEngine;
|
||||
#if UNITY_EDITOR
|
||||
#endif
|
||||
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public interface ITextureExporter
|
||||
{
|
||||
(Byte[] bytes, string mine) GetBytesWithMime(Texture texture, glTFTextureTypes textureType);
|
||||
IEnumerable<(Texture texture, glTFTextureTypes textureType)> GetTextures(Material m);
|
||||
int ExportTexture(glTF gltf, int bufferIndex, Texture texture, glTFTextureTypes textureType);
|
||||
}
|
||||
}
|
||||
@@ -56,6 +56,7 @@ namespace UniGLTF
|
||||
};
|
||||
#endif
|
||||
}
|
||||
|
||||
m_textureFactory = new TextureFactory(loadTextureAsync, externalObjectMap);
|
||||
m_materialFactory = new MaterialFactory(GLTF, Storage, externalObjectMap);
|
||||
}
|
||||
|
||||
@@ -1,12 +0,0 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 99662edfbf59e8f458bcba3b62b13050
|
||||
timeCreated: 1533622882
|
||||
licenseType: Free
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
@@ -1,5 +1,5 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 79721770f23ba6748abc1720cd99ad74
|
||||
guid: 84cb103042e9924459b7dfc465ef4cef
|
||||
folderAsset: yes
|
||||
DefaultImporter:
|
||||
externalObjects: {}
|
||||
@@ -8,6 +8,7 @@ namespace UniGLTF
|
||||
{
|
||||
public static IEnumerable<GetTextureParam> EnumerateTextures(glTF gltf, glTFMaterial m)
|
||||
{
|
||||
int? metallicRoughnessTexture = default;
|
||||
if (m.pbrMetallicRoughness != null)
|
||||
{
|
||||
// base color
|
||||
@@ -17,16 +18,16 @@ namespace UniGLTF
|
||||
}
|
||||
|
||||
// metallic roughness
|
||||
if (m.pbrMetallicRoughness?.metallicRoughnessTexture != null)
|
||||
if (m.pbrMetallicRoughness?.metallicRoughnessTexture != null && m.pbrMetallicRoughness.metallicRoughnessTexture.index != -1)
|
||||
{
|
||||
yield return PBRMaterialItem.MetallicRoughnessTexture(gltf, m);
|
||||
metallicRoughnessTexture = m.pbrMetallicRoughness?.metallicRoughnessTexture?.index;
|
||||
}
|
||||
}
|
||||
|
||||
// emission
|
||||
if (m.emissiveTexture != null)
|
||||
{
|
||||
yield return GetTextureParam.Create(gltf, m.emissiveTexture.index);
|
||||
yield return GetTextureParam.CreateSRGB(gltf, m.emissiveTexture.index);
|
||||
}
|
||||
|
||||
// normal
|
||||
@@ -36,9 +37,16 @@ namespace UniGLTF
|
||||
}
|
||||
|
||||
// occlusion
|
||||
if (m.occlusionTexture != null)
|
||||
int? occlusionTexture = default;
|
||||
if (m.occlusionTexture != null && m.occlusionTexture.index != -1)
|
||||
{
|
||||
yield return PBRMaterialItem.OcclusionTexture(gltf, m);
|
||||
occlusionTexture = m.occlusionTexture.index;
|
||||
}
|
||||
|
||||
// metallicSmooth and occlusion
|
||||
if (metallicRoughnessTexture.HasValue || occlusionTexture.HasValue)
|
||||
{
|
||||
yield return PBRMaterialItem.StandardTexture(gltf, m);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
using System.Collections.Generic;
|
||||
using System;
|
||||
using UniGLTF.UniUnlit;
|
||||
using UniJSON;
|
||||
using UnityEngine;
|
||||
|
||||
|
||||
@@ -15,27 +14,26 @@ namespace UniGLTF
|
||||
|
||||
public interface IMaterialExporter
|
||||
{
|
||||
glTFMaterial ExportMaterial(Material m, TextureExportManager textureManager);
|
||||
glTFMaterial ExportMaterial(Material m, TextureExporter textureManager);
|
||||
}
|
||||
|
||||
public class MaterialExporter : IMaterialExporter
|
||||
{
|
||||
public virtual glTFMaterial ExportMaterial(Material m, TextureExportManager textureManager)
|
||||
public virtual glTFMaterial ExportMaterial(Material m, TextureExporter textureManager)
|
||||
{
|
||||
var material = CreateMaterial(m);
|
||||
|
||||
// common params
|
||||
material.name = m.name;
|
||||
Export_Color(m, textureManager, material);
|
||||
Export_Metallic(m, textureManager, material);
|
||||
Export_Normal(m, textureManager, material);
|
||||
Export_Occlusion(m, textureManager, material);
|
||||
Export_Emission(m, textureManager, material);
|
||||
Export_Normal(m, textureManager, material);
|
||||
Export_OcclusionMetallicRoughness(m, textureManager, material);
|
||||
|
||||
return material;
|
||||
}
|
||||
|
||||
static void Export_Color(Material m, TextureExportManager textureManager, glTFMaterial material)
|
||||
static void Export_Color(Material m, TextureExporter textureManager, glTFMaterial material)
|
||||
{
|
||||
if (m.HasProperty("_Color"))
|
||||
{
|
||||
@@ -44,7 +42,7 @@ namespace UniGLTF
|
||||
|
||||
if (m.HasProperty("_MainTex"))
|
||||
{
|
||||
var index = textureManager.CopyAndGetIndex(m.GetTexture("_MainTex"), RenderTextureReadWrite.sRGB);
|
||||
var index = textureManager.ExportSRGB(m.GetTexture("_MainTex"));
|
||||
if (index != -1)
|
||||
{
|
||||
material.pbrMetallicRoughness.baseColorTexture = new glTFMaterialBaseColorTextureInfo()
|
||||
@@ -57,36 +55,49 @@ namespace UniGLTF
|
||||
}
|
||||
}
|
||||
|
||||
static void Export_Metallic(Material m, TextureExportManager textureManager, glTFMaterial material)
|
||||
/// <summary>
|
||||
/// Occlusion, Metallic, Roughness
|
||||
/// </summary>
|
||||
/// <param name="m"></param>
|
||||
/// <param name="textureManager"></param>
|
||||
/// <param name="material"></param>
|
||||
static void Export_OcclusionMetallicRoughness(Material m, TextureExporter textureManager, glTFMaterial material)
|
||||
{
|
||||
int index = -1;
|
||||
Texture metallicSmoothTexture = default;
|
||||
float smoothness = 1.0f;
|
||||
if (m.HasProperty("_MetallicGlossMap"))
|
||||
{
|
||||
float smoothness = 0.0f;
|
||||
if (m.HasProperty("_GlossMapScale"))
|
||||
{
|
||||
smoothness = m.GetFloat("_GlossMapScale");
|
||||
}
|
||||
metallicSmoothTexture = m.GetTexture("_MetallicGlossMap");
|
||||
}
|
||||
|
||||
// Bake smoothness values into a texture.
|
||||
var converter = new MetallicRoughnessConverter(smoothness);
|
||||
index = textureManager.ConvertAndGetIndex(m.GetTexture("_MetallicGlossMap"), converter);
|
||||
if (index != -1)
|
||||
Texture occlusionTexture = default;
|
||||
var occlusionStrength = 1.0f;
|
||||
if (m.HasProperty("_OcclusionMap"))
|
||||
{
|
||||
occlusionTexture = m.GetTexture("_OcclusionMap");
|
||||
if (occlusionTexture != null && m.HasProperty("_OcclusionStrength"))
|
||||
{
|
||||
material.pbrMetallicRoughness.metallicRoughnessTexture =
|
||||
new glTFMaterialMetallicRoughnessTextureInfo()
|
||||
{
|
||||
index = index,
|
||||
};
|
||||
|
||||
Export_MainTextureTransform(m, material.pbrMetallicRoughness.metallicRoughnessTexture);
|
||||
occlusionStrength = m.GetFloat("_OcclusionStrength");
|
||||
}
|
||||
}
|
||||
|
||||
if (index != -1)
|
||||
int index = textureManager.ExportMetallicSmoothnessOcclusion(metallicSmoothTexture, smoothness, occlusionTexture);
|
||||
|
||||
if (index != -1 && metallicSmoothTexture != null)
|
||||
{
|
||||
material.pbrMetallicRoughness.metallicFactor = 1.0f;
|
||||
material.pbrMetallicRoughness.metallicRoughnessTexture =
|
||||
new glTFMaterialMetallicRoughnessTextureInfo()
|
||||
{
|
||||
index = index,
|
||||
};
|
||||
Export_MainTextureTransform(m, material.pbrMetallicRoughness.metallicRoughnessTexture);
|
||||
|
||||
// Set 1.0f as hard-coded. See: https://github.com/dwango/UniVRM/issues/212.
|
||||
material.pbrMetallicRoughness.metallicFactor = 1.0f;
|
||||
material.pbrMetallicRoughness.roughnessFactor = 1.0f;
|
||||
}
|
||||
else
|
||||
@@ -101,13 +112,23 @@ namespace UniGLTF
|
||||
material.pbrMetallicRoughness.roughnessFactor = 1.0f - m.GetFloat("_Glossiness");
|
||||
}
|
||||
}
|
||||
|
||||
if (index != -1 && occlusionTexture != null)
|
||||
{
|
||||
material.occlusionTexture = new glTFMaterialOcclusionTextureInfo()
|
||||
{
|
||||
index = index,
|
||||
strength = occlusionStrength,
|
||||
};
|
||||
Export_MainTextureTransform(m, material.occlusionTexture);
|
||||
}
|
||||
}
|
||||
|
||||
static void Export_Normal(Material m, TextureExportManager textureManager, glTFMaterial material)
|
||||
static void Export_Normal(Material m, TextureExporter textureManager, glTFMaterial material)
|
||||
{
|
||||
if (m.HasProperty("_BumpMap"))
|
||||
{
|
||||
var index = textureManager.ConvertAndGetIndex(m.GetTexture("_BumpMap"), new NormalConverter());
|
||||
var index = textureManager.ExportNormal(m.GetTexture("_BumpMap"));
|
||||
if (index != -1)
|
||||
{
|
||||
material.normalTexture = new glTFMaterialNormalTextureInfo()
|
||||
@@ -125,29 +146,7 @@ namespace UniGLTF
|
||||
}
|
||||
}
|
||||
|
||||
static void Export_Occlusion(Material m, TextureExportManager textureManager, glTFMaterial material)
|
||||
{
|
||||
if (m.HasProperty("_OcclusionMap"))
|
||||
{
|
||||
var index = textureManager.ConvertAndGetIndex(m.GetTexture("_OcclusionMap"), new OcclusionConverter());
|
||||
if (index != -1)
|
||||
{
|
||||
material.occlusionTexture = new glTFMaterialOcclusionTextureInfo()
|
||||
{
|
||||
index = index,
|
||||
};
|
||||
|
||||
Export_MainTextureTransform(m, material.occlusionTexture);
|
||||
}
|
||||
|
||||
if (index != -1 && m.HasProperty("_OcclusionStrength"))
|
||||
{
|
||||
material.occlusionTexture.strength = m.GetFloat("_OcclusionStrength");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void Export_Emission(Material m, TextureExportManager textureManager, glTFMaterial material)
|
||||
static void Export_Emission(Material m, TextureExporter textureManager, glTFMaterial material)
|
||||
{
|
||||
if (m.IsKeywordEnabled("_EMISSION") == false)
|
||||
return;
|
||||
@@ -164,7 +163,7 @@ namespace UniGLTF
|
||||
|
||||
if (m.HasProperty("_EmissionMap"))
|
||||
{
|
||||
var index = textureManager.CopyAndGetIndex(m.GetTexture("_EmissionMap"), RenderTextureReadWrite.sRGB);
|
||||
var index = textureManager.ExportSRGB(m.GetTexture("_EmissionMap"));
|
||||
if (index != -1)
|
||||
{
|
||||
material.emissiveTexture = new glTFMaterialEmissiveTextureInfo()
|
||||
@@ -1,5 +1,5 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 9968c71baa1b1c04c94b0d3191cf513a
|
||||
guid: 89f71b1d593633c47bfd4cfef050ae0d
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
230
Assets/UniGLTF/Runtime/UniGLTF/IO/MaterialIO/PBRMaterialItem.cs
Normal file
230
Assets/UniGLTF/Runtime/UniGLTF/IO/MaterialIO/PBRMaterialItem.cs
Normal file
@@ -0,0 +1,230 @@
|
||||
|
||||
using System.Threading.Tasks;
|
||||
using UnityEngine;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
/// StandardShader variables
|
||||
///
|
||||
/// _Color
|
||||
/// _MainTex
|
||||
/// _Cutoff
|
||||
/// _Glossiness
|
||||
/// _Metallic
|
||||
/// _MetallicGlossMap
|
||||
/// _BumpScale
|
||||
/// _BumpMap
|
||||
/// _Parallax
|
||||
/// _ParallaxMap
|
||||
/// _OcclusionStrength
|
||||
/// _OcclusionMap
|
||||
/// _EmissionColor
|
||||
/// _EmissionMap
|
||||
/// _DetailMask
|
||||
/// _DetailAlbedoMap
|
||||
/// _DetailNormalMapScale
|
||||
/// _DetailNormalMap
|
||||
/// _UVSec
|
||||
/// _EmissionScaleUI
|
||||
/// _EmissionColorUI
|
||||
/// _Mode
|
||||
/// _SrcBlend
|
||||
/// _DstBlend
|
||||
/// _ZWrite
|
||||
public static class PBRMaterialItem
|
||||
{
|
||||
public const string ShaderName = "Standard";
|
||||
|
||||
private enum BlendMode
|
||||
{
|
||||
Opaque,
|
||||
Cutout,
|
||||
Fade,
|
||||
Transparent
|
||||
}
|
||||
|
||||
public static GetTextureParam BaseColorTexture(glTF gltf, glTFMaterial src)
|
||||
{
|
||||
return GetTextureParam.CreateSRGB(gltf, src.pbrMetallicRoughness.baseColorTexture.index);
|
||||
}
|
||||
|
||||
public static GetTextureParam StandardTexture(glTF gltf, glTFMaterial src)
|
||||
{
|
||||
var metallicFactor = 1.0f;
|
||||
var roughnessFactor = 1.0f;
|
||||
if (src.pbrMetallicRoughness != null)
|
||||
{
|
||||
metallicFactor = src.pbrMetallicRoughness.metallicFactor;
|
||||
roughnessFactor = src.pbrMetallicRoughness.roughnessFactor;
|
||||
}
|
||||
return GetTextureParam.CreateStandard(gltf,
|
||||
src.pbrMetallicRoughness?.metallicRoughnessTexture?.index,
|
||||
src.occlusionTexture?.index,
|
||||
metallicFactor,
|
||||
roughnessFactor);
|
||||
}
|
||||
|
||||
public static GetTextureParam NormalTexture(glTF gltf, glTFMaterial src)
|
||||
{
|
||||
return GetTextureParam.CreateNormal(gltf, src.normalTexture.index);
|
||||
}
|
||||
|
||||
public static async Task<Material> CreateAsync(IAwaitCaller awaitCaller, glTF gltf, int i, GetTextureAsyncFunc getTexture)
|
||||
{
|
||||
if (getTexture == null)
|
||||
{
|
||||
getTexture = (IAwaitCaller _awaitCaller, glTF _gltf, GetTextureParam _param) => Task.FromResult<Texture2D>(null);
|
||||
}
|
||||
|
||||
if (i < 0 || i >= gltf.materials.Count)
|
||||
{
|
||||
return MaterialFactory.CreateMaterial(i, null, ShaderName);
|
||||
}
|
||||
|
||||
var src = gltf.materials[i];
|
||||
var material = MaterialFactory.CreateMaterial(i, src, ShaderName);
|
||||
var standardParam = default(GetTextureParam);
|
||||
if (src.pbrMetallicRoughness != null || src.occlusionTexture != null)
|
||||
{
|
||||
if (src.pbrMetallicRoughness.metallicRoughnessTexture != null || src.occlusionTexture != null)
|
||||
{
|
||||
standardParam = StandardTexture(gltf, src);
|
||||
}
|
||||
if (src.pbrMetallicRoughness.baseColorFactor != null && src.pbrMetallicRoughness.baseColorFactor.Length == 4)
|
||||
{
|
||||
var color = src.pbrMetallicRoughness.baseColorFactor;
|
||||
material.color = (new Color(color[0], color[1], color[2], color[3])).gamma;
|
||||
}
|
||||
|
||||
if (src.pbrMetallicRoughness.baseColorTexture != null && src.pbrMetallicRoughness.baseColorTexture.index != -1)
|
||||
{
|
||||
material.mainTexture = await getTexture(awaitCaller, gltf, BaseColorTexture(gltf, src));
|
||||
|
||||
// Texture Offset and Scale
|
||||
MaterialFactory.SetTextureOffsetAndScale(material, src.pbrMetallicRoughness.baseColorTexture, "_MainTex");
|
||||
}
|
||||
|
||||
if (src.pbrMetallicRoughness.metallicRoughnessTexture != null && src.pbrMetallicRoughness.metallicRoughnessTexture.index != -1)
|
||||
{
|
||||
material.EnableKeyword("_METALLICGLOSSMAP");
|
||||
|
||||
var texture = await getTexture(awaitCaller, gltf, standardParam);
|
||||
if (texture != null)
|
||||
{
|
||||
material.SetTexture(GetTextureParam.METALLIC_GLOSS_PROP, texture);
|
||||
}
|
||||
|
||||
material.SetFloat("_Metallic", 1.0f);
|
||||
// Set 1.0f as hard-coded. See: https://github.com/dwango/UniVRM/issues/212.
|
||||
material.SetFloat("_GlossMapScale", 1.0f);
|
||||
|
||||
// Texture Offset and Scale
|
||||
MaterialFactory.SetTextureOffsetAndScale(material, src.pbrMetallicRoughness.metallicRoughnessTexture, "_MetallicGlossMap");
|
||||
}
|
||||
else
|
||||
{
|
||||
material.SetFloat("_Metallic", src.pbrMetallicRoughness.metallicFactor);
|
||||
material.SetFloat("_Glossiness", 1.0f - src.pbrMetallicRoughness.roughnessFactor);
|
||||
}
|
||||
}
|
||||
|
||||
if (src.normalTexture != null && src.normalTexture.index != -1)
|
||||
{
|
||||
material.EnableKeyword("_NORMALMAP");
|
||||
var texture = await getTexture(awaitCaller, gltf, NormalTexture(gltf, src));
|
||||
if (texture != null)
|
||||
{
|
||||
material.SetTexture(GetTextureParam.NORMAL_PROP, texture);
|
||||
material.SetFloat("_BumpScale", src.normalTexture.scale);
|
||||
}
|
||||
|
||||
// Texture Offset and Scale
|
||||
MaterialFactory.SetTextureOffsetAndScale(material, src.normalTexture, "_BumpMap");
|
||||
}
|
||||
|
||||
if (src.occlusionTexture != null && src.occlusionTexture.index != -1)
|
||||
{
|
||||
var texture = await getTexture(awaitCaller, gltf, standardParam);
|
||||
if (texture != null)
|
||||
{
|
||||
material.SetTexture(GetTextureParam.OCCLUSION_PROP, texture);
|
||||
material.SetFloat("_OcclusionStrength", src.occlusionTexture.strength);
|
||||
}
|
||||
|
||||
// Texture Offset and Scale
|
||||
MaterialFactory.SetTextureOffsetAndScale(material, src.occlusionTexture, "_OcclusionMap");
|
||||
}
|
||||
|
||||
if (src.emissiveFactor != null
|
||||
|| (src.emissiveTexture != null && src.emissiveTexture.index != -1))
|
||||
{
|
||||
material.EnableKeyword("_EMISSION");
|
||||
material.globalIlluminationFlags &= ~MaterialGlobalIlluminationFlags.EmissiveIsBlack;
|
||||
|
||||
if (src.emissiveFactor != null && src.emissiveFactor.Length == 3)
|
||||
{
|
||||
material.SetColor("_EmissionColor", new Color(src.emissiveFactor[0], src.emissiveFactor[1], src.emissiveFactor[2]));
|
||||
}
|
||||
|
||||
if (src.emissiveTexture != null && src.emissiveTexture.index != -1)
|
||||
{
|
||||
var texture = await getTexture(awaitCaller, gltf, GetTextureParam.CreateSRGB(gltf, src.emissiveTexture.index));
|
||||
if (texture != null)
|
||||
{
|
||||
material.SetTexture("_EmissionMap", texture);
|
||||
}
|
||||
|
||||
// Texture Offset and Scale
|
||||
MaterialFactory.SetTextureOffsetAndScale(material, src.emissiveTexture, "_EmissionMap");
|
||||
}
|
||||
}
|
||||
|
||||
BlendMode blendMode = BlendMode.Opaque;
|
||||
// https://forum.unity.com/threads/standard-material-shader-ignoring-setfloat-property-_mode.344557/#post-2229980
|
||||
switch (src.alphaMode)
|
||||
{
|
||||
case "BLEND":
|
||||
blendMode = BlendMode.Fade;
|
||||
material.SetOverrideTag("RenderType", "Transparent");
|
||||
material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.SrcAlpha);
|
||||
material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.OneMinusSrcAlpha);
|
||||
material.SetInt("_ZWrite", 0);
|
||||
material.DisableKeyword("_ALPHATEST_ON");
|
||||
material.EnableKeyword("_ALPHABLEND_ON");
|
||||
material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
|
||||
material.renderQueue = 3000;
|
||||
break;
|
||||
|
||||
case "MASK":
|
||||
blendMode = BlendMode.Cutout;
|
||||
material.SetOverrideTag("RenderType", "TransparentCutout");
|
||||
material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
|
||||
material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.Zero);
|
||||
material.SetInt("_ZWrite", 1);
|
||||
material.SetFloat("_Cutoff", src.alphaCutoff);
|
||||
material.EnableKeyword("_ALPHATEST_ON");
|
||||
material.DisableKeyword("_ALPHABLEND_ON");
|
||||
material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
|
||||
material.renderQueue = 2450;
|
||||
|
||||
break;
|
||||
|
||||
default: // OPAQUE
|
||||
blendMode = BlendMode.Opaque;
|
||||
material.SetOverrideTag("RenderType", "");
|
||||
material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
|
||||
material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.Zero);
|
||||
material.SetInt("_ZWrite", 1);
|
||||
material.DisableKeyword("_ALPHATEST_ON");
|
||||
material.DisableKeyword("_ALPHABLEND_ON");
|
||||
material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
|
||||
material.renderQueue = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
material.SetFloat("_Mode", (float)blendMode);
|
||||
|
||||
return material;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -21,7 +21,7 @@ namespace UniGLTF
|
||||
// texture
|
||||
if (src.pbrMetallicRoughness.baseColorTexture != null)
|
||||
{
|
||||
material.mainTexture = await getTexture(awaitCaller, gltf, GetTextureParam.Create(gltf, src.pbrMetallicRoughness.baseColorTexture.index));
|
||||
material.mainTexture = await getTexture(awaitCaller, gltf, GetTextureParam.CreateSRGB(gltf, src.pbrMetallicRoughness.baseColorTexture.index));
|
||||
|
||||
// Texture Offset and Scale
|
||||
MaterialFactory.SetTextureOffsetAndScale(material, src.pbrMetallicRoughness.baseColorTexture, "_MainTex");
|
||||
@@ -1,8 +0,0 @@
|
||||
fileFormatVersion: 2
|
||||
guid: bafc2eb5323419940a4991a8045bedc3
|
||||
folderAsset: yes
|
||||
DefaultImporter:
|
||||
externalObjects: {}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
@@ -1,225 +0,0 @@
|
||||
|
||||
using System.Threading.Tasks;
|
||||
using UnityEngine;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
/// StandardShader variables
|
||||
///
|
||||
/// _Color
|
||||
/// _MainTex
|
||||
/// _Cutoff
|
||||
/// _Glossiness
|
||||
/// _Metallic
|
||||
/// _MetallicGlossMap
|
||||
/// _BumpScale
|
||||
/// _BumpMap
|
||||
/// _Parallax
|
||||
/// _ParallaxMap
|
||||
/// _OcclusionStrength
|
||||
/// _OcclusionMap
|
||||
/// _EmissionColor
|
||||
/// _EmissionMap
|
||||
/// _DetailMask
|
||||
/// _DetailAlbedoMap
|
||||
/// _DetailNormalMapScale
|
||||
/// _DetailNormalMap
|
||||
/// _UVSec
|
||||
/// _EmissionScaleUI
|
||||
/// _EmissionColorUI
|
||||
/// _Mode
|
||||
/// _SrcBlend
|
||||
/// _DstBlend
|
||||
/// _ZWrite
|
||||
public static class PBRMaterialItem
|
||||
{
|
||||
public const string ShaderName = "Standard";
|
||||
|
||||
private enum BlendMode
|
||||
{
|
||||
Opaque,
|
||||
Cutout,
|
||||
Fade,
|
||||
Transparent
|
||||
}
|
||||
|
||||
public static GetTextureParam BaseColorTexture(glTF gltf, glTFMaterial src)
|
||||
{
|
||||
return GetTextureParam.Create(gltf, src.pbrMetallicRoughness.baseColorTexture.index);
|
||||
}
|
||||
|
||||
public static GetTextureParam MetallicRoughnessTexture(glTF gltf, glTFMaterial src)
|
||||
{
|
||||
return GetTextureParam.CreateMetallic(gltf,
|
||||
src.pbrMetallicRoughness.metallicRoughnessTexture.index,
|
||||
src.pbrMetallicRoughness.metallicFactor);
|
||||
}
|
||||
|
||||
public static GetTextureParam OcclusionTexture(glTF gltf, glTFMaterial src)
|
||||
{
|
||||
return GetTextureParam.CreateOcclusion(gltf, src.occlusionTexture.index);
|
||||
}
|
||||
|
||||
public static GetTextureParam NormalTexture(glTF gltf, glTFMaterial src)
|
||||
{
|
||||
return GetTextureParam.CreateNormal(gltf, src.normalTexture.index);
|
||||
}
|
||||
|
||||
public static async Task<Material> CreateAsync(IAwaitCaller awaitCaller, glTF gltf, int i, GetTextureAsyncFunc getTexture)
|
||||
{
|
||||
if (getTexture == null)
|
||||
{
|
||||
getTexture = (_x, _y, _z) => Task.FromResult<Texture2D>(null);
|
||||
}
|
||||
|
||||
// PBR material
|
||||
var material = default(Material);
|
||||
if (i >= 0 && i < gltf.materials.Count)
|
||||
{
|
||||
var src = gltf.materials[i];
|
||||
material = MaterialFactory.CreateMaterial(i, src, ShaderName);
|
||||
if (src.pbrMetallicRoughness != null)
|
||||
{
|
||||
if (src.pbrMetallicRoughness.baseColorFactor != null && src.pbrMetallicRoughness.baseColorFactor.Length == 4)
|
||||
{
|
||||
var color = src.pbrMetallicRoughness.baseColorFactor;
|
||||
material.color = (new Color(color[0], color[1], color[2], color[3])).gamma;
|
||||
}
|
||||
|
||||
if (src.pbrMetallicRoughness.baseColorTexture != null && src.pbrMetallicRoughness.baseColorTexture.index != -1)
|
||||
{
|
||||
material.mainTexture = await getTexture(awaitCaller, gltf, BaseColorTexture(gltf, src));
|
||||
|
||||
// Texture Offset and Scale
|
||||
MaterialFactory.SetTextureOffsetAndScale(material, src.pbrMetallicRoughness.baseColorTexture, "_MainTex");
|
||||
}
|
||||
|
||||
if (src.pbrMetallicRoughness.metallicRoughnessTexture != null && src.pbrMetallicRoughness.metallicRoughnessTexture.index != -1)
|
||||
{
|
||||
material.EnableKeyword("_METALLICGLOSSMAP");
|
||||
|
||||
var texture = await getTexture(awaitCaller, gltf, MetallicRoughnessTexture(gltf, src));
|
||||
if (texture != null)
|
||||
{
|
||||
material.SetTexture(GetTextureParam.METALLIC_GLOSS_PROP, texture);
|
||||
}
|
||||
|
||||
material.SetFloat("_Metallic", 1.0f);
|
||||
// Set 1.0f as hard-coded. See: https://github.com/dwango/UniVRM/issues/212.
|
||||
material.SetFloat("_GlossMapScale", 1.0f);
|
||||
|
||||
// Texture Offset and Scale
|
||||
MaterialFactory.SetTextureOffsetAndScale(material, src.pbrMetallicRoughness.metallicRoughnessTexture, "_MetallicGlossMap");
|
||||
}
|
||||
else
|
||||
{
|
||||
material.SetFloat("_Metallic", src.pbrMetallicRoughness.metallicFactor);
|
||||
material.SetFloat("_Glossiness", 1.0f - src.pbrMetallicRoughness.roughnessFactor);
|
||||
}
|
||||
}
|
||||
|
||||
if (src.normalTexture != null && src.normalTexture.index != -1)
|
||||
{
|
||||
material.EnableKeyword("_NORMALMAP");
|
||||
var texture = await getTexture(awaitCaller, gltf, NormalTexture(gltf, src));
|
||||
if (texture != null)
|
||||
{
|
||||
material.SetTexture(GetTextureParam.NORMAL_PROP, texture);
|
||||
material.SetFloat("_BumpScale", src.normalTexture.scale);
|
||||
}
|
||||
|
||||
// Texture Offset and Scale
|
||||
MaterialFactory.SetTextureOffsetAndScale(material, src.normalTexture, "_BumpMap");
|
||||
}
|
||||
|
||||
if (src.occlusionTexture != null && src.occlusionTexture.index != -1)
|
||||
{
|
||||
var texture = await getTexture(awaitCaller, gltf, OcclusionTexture(gltf, src));
|
||||
if (texture != null)
|
||||
{
|
||||
material.SetTexture(GetTextureParam.OCCLUSION_PROP, texture);
|
||||
material.SetFloat("_OcclusionStrength", src.occlusionTexture.strength);
|
||||
}
|
||||
|
||||
// Texture Offset and Scale
|
||||
MaterialFactory.SetTextureOffsetAndScale(material, src.occlusionTexture, "_OcclusionMap");
|
||||
}
|
||||
|
||||
if (src.emissiveFactor != null
|
||||
|| (src.emissiveTexture != null && src.emissiveTexture.index != -1))
|
||||
{
|
||||
material.EnableKeyword("_EMISSION");
|
||||
material.globalIlluminationFlags &= ~MaterialGlobalIlluminationFlags.EmissiveIsBlack;
|
||||
|
||||
if (src.emissiveFactor != null && src.emissiveFactor.Length == 3)
|
||||
{
|
||||
material.SetColor("_EmissionColor", new Color(src.emissiveFactor[0], src.emissiveFactor[1], src.emissiveFactor[2]));
|
||||
}
|
||||
|
||||
if (src.emissiveTexture != null && src.emissiveTexture.index != -1)
|
||||
{
|
||||
var texture = await getTexture(awaitCaller, gltf, GetTextureParam.Create(gltf, src.emissiveTexture.index));
|
||||
if (texture != null)
|
||||
{
|
||||
material.SetTexture("_EmissionMap", texture);
|
||||
}
|
||||
|
||||
// Texture Offset and Scale
|
||||
MaterialFactory.SetTextureOffsetAndScale(material, src.emissiveTexture, "_EmissionMap");
|
||||
}
|
||||
}
|
||||
|
||||
BlendMode blendMode = BlendMode.Opaque;
|
||||
// https://forum.unity.com/threads/standard-material-shader-ignoring-setfloat-property-_mode.344557/#post-2229980
|
||||
switch (src.alphaMode)
|
||||
{
|
||||
case "BLEND":
|
||||
blendMode = BlendMode.Fade;
|
||||
material.SetOverrideTag("RenderType", "Transparent");
|
||||
material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.SrcAlpha);
|
||||
material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.OneMinusSrcAlpha);
|
||||
material.SetInt("_ZWrite", 0);
|
||||
material.DisableKeyword("_ALPHATEST_ON");
|
||||
material.EnableKeyword("_ALPHABLEND_ON");
|
||||
material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
|
||||
material.renderQueue = 3000;
|
||||
break;
|
||||
|
||||
case "MASK":
|
||||
blendMode = BlendMode.Cutout;
|
||||
material.SetOverrideTag("RenderType", "TransparentCutout");
|
||||
material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
|
||||
material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.Zero);
|
||||
material.SetInt("_ZWrite", 1);
|
||||
material.SetFloat("_Cutoff", src.alphaCutoff);
|
||||
material.EnableKeyword("_ALPHATEST_ON");
|
||||
material.DisableKeyword("_ALPHABLEND_ON");
|
||||
material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
|
||||
material.renderQueue = 2450;
|
||||
|
||||
break;
|
||||
|
||||
default: // OPAQUE
|
||||
blendMode = BlendMode.Opaque;
|
||||
material.SetOverrideTag("RenderType", "");
|
||||
material.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.One);
|
||||
material.SetInt("_DstBlend", (int)UnityEngine.Rendering.BlendMode.Zero);
|
||||
material.SetInt("_ZWrite", 1);
|
||||
material.DisableKeyword("_ALPHATEST_ON");
|
||||
material.DisableKeyword("_ALPHABLEND_ON");
|
||||
material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
|
||||
material.renderQueue = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
material.SetFloat("_Mode", (float)blendMode);
|
||||
}
|
||||
else
|
||||
{
|
||||
material = MaterialFactory.CreateMaterial(i, null, ShaderName);
|
||||
}
|
||||
|
||||
return material;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,10 +0,0 @@
|
||||
using UnityEngine;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public interface ITextureConverter
|
||||
{
|
||||
Texture2D GetImportTexture(Texture2D texture);
|
||||
Texture2D GetExportTexture(Texture2D texture);
|
||||
}
|
||||
}
|
||||
@@ -1,67 +0,0 @@
|
||||
using UnityEngine;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public class MetallicRoughnessConverter : ITextureConverter
|
||||
{
|
||||
private float _smoothnessOrRoughness;
|
||||
|
||||
public MetallicRoughnessConverter(float smoothnessOrRoughness)
|
||||
{
|
||||
_smoothnessOrRoughness = smoothnessOrRoughness;
|
||||
}
|
||||
|
||||
public Texture2D GetImportTexture(Texture2D texture)
|
||||
{
|
||||
var converted = TextureConverter.Convert(texture, glTFTextureTypes.Metallic, Import, null);
|
||||
return converted;
|
||||
}
|
||||
|
||||
public Texture2D GetExportTexture(Texture2D texture)
|
||||
{
|
||||
var converted = TextureConverter.Convert(texture, glTFTextureTypes.Metallic, Export, null);
|
||||
return converted;
|
||||
}
|
||||
|
||||
public Color32 Import(Color32 src)
|
||||
{
|
||||
// Roughness(glTF): dst.g -> Smoothness(Unity): src.a (with conversion)
|
||||
// Metallic(glTF) : dst.b -> Metallic(Unity) : src.r
|
||||
|
||||
var pixelRoughnessFactor = (src.g * _smoothnessOrRoughness) / 255.0f; // roughness
|
||||
var pixelSmoothness = 1.0f - Mathf.Sqrt(pixelRoughnessFactor);
|
||||
|
||||
return new Color32
|
||||
{
|
||||
r = src.b,
|
||||
g = 0,
|
||||
b = 0,
|
||||
// Bake roughness values into a texture.
|
||||
// See: https://github.com/dwango/UniVRM/issues/212.
|
||||
a = (byte)Mathf.Clamp(pixelSmoothness * 255, 0, 255),
|
||||
};
|
||||
}
|
||||
|
||||
public Color32 Export(Color32 src)
|
||||
{
|
||||
// Smoothness(Unity): src.a -> Roughness(glTF): dst.g (with conversion)
|
||||
// Metallic(Unity) : src.r -> Metallic(glTF) : dst.b
|
||||
|
||||
var pixelSmoothness = (src.a * _smoothnessOrRoughness) / 255.0f; // smoothness
|
||||
// https://blogs.unity3d.com/jp/2016/01/25/ggx-in-unity-5-3/
|
||||
var pixelRoughnessFactorSqrt = (1.0f - pixelSmoothness);
|
||||
var pixelRoughnessFactor = pixelRoughnessFactorSqrt * pixelRoughnessFactorSqrt;
|
||||
|
||||
return new Color32
|
||||
{
|
||||
r = 0,
|
||||
// Bake smoothness values into a texture.
|
||||
// See: https://github.com/dwango/UniVRM/issues/212.
|
||||
g = (byte)Mathf.Clamp(pixelRoughnessFactor * 255, 0, 255),
|
||||
b = src.r,
|
||||
a = 255,
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,46 +0,0 @@
|
||||
using UnityEngine;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public class NormalConverter : ITextureConverter
|
||||
{
|
||||
private Material m_decoder;
|
||||
private Material GetDecoder()
|
||||
{
|
||||
if (m_decoder == null)
|
||||
{
|
||||
m_decoder = new Material(Shader.Find("UniGLTF/NormalMapDecoder"));
|
||||
}
|
||||
return m_decoder;
|
||||
}
|
||||
|
||||
private Material m_encoder;
|
||||
private Material GetEncoder()
|
||||
{
|
||||
if (m_encoder == null)
|
||||
{
|
||||
m_encoder = new Material(Shader.Find("UniGLTF/NormalMapEncoder"));
|
||||
}
|
||||
return m_encoder;
|
||||
}
|
||||
|
||||
// GLTF data to Unity texture
|
||||
// ConvertToNormalValueFromRawColorWhenCompressionIsRequired
|
||||
public Texture2D GetImportTexture(Texture2D texture)
|
||||
{
|
||||
var mat = GetEncoder();
|
||||
var converted = TextureConverter.Convert(texture, glTFTextureTypes.Normal, null, mat);
|
||||
return converted;
|
||||
}
|
||||
|
||||
// Unity texture to GLTF data
|
||||
// ConvertToRawColorWhenNormalValueIsCompressed
|
||||
public Texture2D GetExportTexture(Texture2D texture)
|
||||
{
|
||||
var mat = GetDecoder();
|
||||
var converted = TextureConverter.Convert(texture, glTFTextureTypes.Normal, null, mat);
|
||||
return converted;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,42 +0,0 @@
|
||||
using UnityEngine;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public class OcclusionConverter : ITextureConverter
|
||||
{
|
||||
|
||||
public Texture2D GetImportTexture(Texture2D texture)
|
||||
{
|
||||
var converted = TextureConverter.Convert(texture, glTFTextureTypes.Occlusion, Import, null);
|
||||
return converted;
|
||||
}
|
||||
|
||||
public Texture2D GetExportTexture(Texture2D texture)
|
||||
{
|
||||
var converted = TextureConverter.Convert(texture, glTFTextureTypes.Occlusion, Export, null);
|
||||
return converted;
|
||||
}
|
||||
|
||||
public Color32 Import(Color32 src)
|
||||
{
|
||||
return new Color32
|
||||
{
|
||||
r = 0,
|
||||
g = src.r,
|
||||
b = 0,
|
||||
a = 255,
|
||||
};
|
||||
}
|
||||
|
||||
public Color32 Export(Color32 src)
|
||||
{
|
||||
return new Color32
|
||||
{
|
||||
r = src.g,
|
||||
g = 0,
|
||||
b = 0,
|
||||
a = 255,
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,92 +0,0 @@
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using UnityEngine;
|
||||
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public class TextureExportManager
|
||||
{
|
||||
List<Texture> m_textures;
|
||||
public List<Texture> Textures
|
||||
{
|
||||
get { return m_textures; }
|
||||
}
|
||||
|
||||
List<Texture> m_exportTextures;
|
||||
public Texture GetExportTexture(int index)
|
||||
{
|
||||
if (index < 0 || index >= m_exportTextures.Count)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
if (m_exportTextures[index] != null)
|
||||
{
|
||||
// コピー変換済み
|
||||
return m_exportTextures[index];
|
||||
}
|
||||
|
||||
// オリジナル
|
||||
return m_textures[index];
|
||||
}
|
||||
|
||||
public TextureExportManager(IEnumerable<Texture> textures)
|
||||
{
|
||||
if (textures == null)
|
||||
{
|
||||
// empty list for UnitTest
|
||||
textures = new Texture[] { };
|
||||
}
|
||||
m_textures = textures.ToList();
|
||||
m_exportTextures = new List<Texture>(Enumerable.Repeat<Texture>(null, m_textures.Count));
|
||||
}
|
||||
|
||||
public int CopyAndGetIndex(Texture texture, RenderTextureReadWrite readWrite)
|
||||
{
|
||||
if (texture == null)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
var index = m_textures.IndexOf(texture);
|
||||
if (index == -1)
|
||||
{
|
||||
// ありえない?
|
||||
return -1;
|
||||
}
|
||||
|
||||
#if UNITY_EDITOR
|
||||
if (!string.IsNullOrEmpty(UnityEditor.AssetDatabase.GetAssetPath(texture)))
|
||||
{
|
||||
m_exportTextures[index] = texture;
|
||||
return index;
|
||||
}
|
||||
#endif
|
||||
|
||||
// ToDo: may already exists
|
||||
m_exportTextures[index] = TextureConverter.CopyTexture(texture, readWrite, null);
|
||||
|
||||
return index;
|
||||
}
|
||||
|
||||
public int ConvertAndGetIndex(Texture texture, ITextureConverter converter)
|
||||
{
|
||||
if (texture == null)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
var index = m_textures.IndexOf(texture);
|
||||
if (index == -1)
|
||||
{
|
||||
// ありえない?
|
||||
return -1;
|
||||
}
|
||||
|
||||
m_exportTextures[index] = converter.GetExportTexture(texture as Texture2D);
|
||||
|
||||
return index;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,12 +0,0 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 435499f173753ac418331fe0f967b789
|
||||
timeCreated: 1541561421
|
||||
licenseType: Free
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
@@ -1,189 +0,0 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using UnityEngine;
|
||||
#if UNITY_EDITOR
|
||||
using System.Reflection;
|
||||
using UnityEditor;
|
||||
#endif
|
||||
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
|
||||
public class TextureIO : ITextureExporter
|
||||
{
|
||||
public static RenderTextureReadWrite GetColorSpace(glTFTextureTypes textureType)
|
||||
{
|
||||
switch (textureType)
|
||||
{
|
||||
case glTFTextureTypes.Metallic:
|
||||
case glTFTextureTypes.Normal:
|
||||
case glTFTextureTypes.Occlusion:
|
||||
return RenderTextureReadWrite.Linear;
|
||||
case glTFTextureTypes.BaseColor:
|
||||
case glTFTextureTypes.Emissive:
|
||||
return RenderTextureReadWrite.sRGB;
|
||||
default:
|
||||
return RenderTextureReadWrite.sRGB;
|
||||
}
|
||||
}
|
||||
|
||||
public static glTFTextureTypes GetglTFTextureType(string shaderName, string propName)
|
||||
{
|
||||
switch (propName)
|
||||
{
|
||||
case "_Color":
|
||||
return glTFTextureTypes.BaseColor;
|
||||
case "_MetallicGlossMap":
|
||||
return glTFTextureTypes.Metallic;
|
||||
case "_BumpMap":
|
||||
return glTFTextureTypes.Normal;
|
||||
case "_OcclusionMap":
|
||||
return glTFTextureTypes.Occlusion;
|
||||
case "_EmissionMap":
|
||||
return glTFTextureTypes.Emissive;
|
||||
default:
|
||||
return glTFTextureTypes.Unknown;
|
||||
}
|
||||
}
|
||||
|
||||
public static glTFTextureTypes GetglTFTextureType(glTF glTf, int textureIndex)
|
||||
{
|
||||
foreach (var material in glTf.materials)
|
||||
{
|
||||
var textureInfo = material.GetTextures().FirstOrDefault(x => (x != null) && x.index == textureIndex);
|
||||
if (textureInfo != null)
|
||||
{
|
||||
return textureInfo.TextureType;
|
||||
}
|
||||
}
|
||||
return glTFTextureTypes.Unknown;
|
||||
}
|
||||
|
||||
#if UNITY_EDITOR
|
||||
public static void MarkTextureAssetAsNormalMap(string assetPath)
|
||||
{
|
||||
if (string.IsNullOrEmpty(assetPath))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var textureImporter = AssetImporter.GetAtPath(assetPath) as TextureImporter;
|
||||
if (null == textureImporter)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
//Debug.LogFormat("[MarkTextureAssetAsNormalMap] {0}", assetPath);
|
||||
textureImporter.textureType = TextureImporterType.NormalMap;
|
||||
textureImporter.SaveAndReimport();
|
||||
}
|
||||
#endif
|
||||
|
||||
public virtual IEnumerable<(Texture texture, glTFTextureTypes textureType)> GetTextures(Material m)
|
||||
{
|
||||
var props = ShaderPropExporter.PreShaderPropExporter.GetPropsForSupportedShader(m.shader.name);
|
||||
if (props == null)
|
||||
{
|
||||
yield return (m.mainTexture, glTFTextureTypes.BaseColor);
|
||||
}
|
||||
|
||||
foreach (var prop in props.Properties)
|
||||
{
|
||||
|
||||
if (prop.ShaderPropertyType == ShaderPropExporter.ShaderPropertyType.TexEnv)
|
||||
{
|
||||
yield return (m.GetTexture(prop.Key), GetglTFTextureType(m.shader.name, prop.Key));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public virtual (Byte[] bytes, string mine) GetBytesWithMime(Texture texture, glTFTextureTypes textureType)
|
||||
{
|
||||
#if UNITY_EDITOR
|
||||
var path = UnityPath.FromAsset(texture);
|
||||
if (path.IsUnderAssetsFolder)
|
||||
{
|
||||
var textureImporter = AssetImporter.GetAtPath(path.Value) as TextureImporter;
|
||||
var getSizeMethod = typeof(TextureImporter).GetMethod("GetWidthAndHeight", BindingFlags.NonPublic | BindingFlags.Instance);
|
||||
if (textureImporter != null && getSizeMethod != null)
|
||||
{
|
||||
var args = new object[2] { 0, 0 };
|
||||
getSizeMethod.Invoke(textureImporter, args);
|
||||
var originalWidth = (int)args[0];
|
||||
var originalHeight = (int)args[1];
|
||||
|
||||
var originalSize = Mathf.Max(originalWidth, originalHeight);
|
||||
var requiredMaxSize = textureImporter.maxTextureSize;
|
||||
|
||||
// Resized exporting if MaxSize setting value is smaller than original image size.
|
||||
if (originalSize > requiredMaxSize)
|
||||
{
|
||||
return
|
||||
(
|
||||
TextureConverter.CopyTexture(texture, GetColorSpace(textureType), null).EncodeToPNG(),
|
||||
"image/png"
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
if (path.Extension == ".png")
|
||||
{
|
||||
return
|
||||
(
|
||||
System.IO.File.ReadAllBytes(path.FullPath),
|
||||
"image/png"
|
||||
);
|
||||
}
|
||||
if (path.Extension == ".jpg")
|
||||
{
|
||||
return
|
||||
(
|
||||
System.IO.File.ReadAllBytes(path.FullPath),
|
||||
"image/jpeg"
|
||||
);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
return
|
||||
(
|
||||
TextureConverter.CopyTexture(texture, TextureIO.GetColorSpace(textureType), null).EncodeToPNG(),
|
||||
"image/png"
|
||||
);
|
||||
}
|
||||
|
||||
public int ExportTexture(glTF gltf, int bufferIndex, Texture texture, glTFTextureTypes textureType)
|
||||
{
|
||||
var bytesWithMime = GetBytesWithMime(texture, textureType); ;
|
||||
|
||||
// add view
|
||||
var view = gltf.buffers[bufferIndex].Append(bytesWithMime.bytes, glBufferTarget.NONE);
|
||||
var viewIndex = gltf.AddBufferView(view);
|
||||
|
||||
// add image
|
||||
var imageIndex = gltf.images.Count;
|
||||
gltf.images.Add(new glTFImage
|
||||
{
|
||||
name = GetTextureParam.RemoveSuffix(texture.name),
|
||||
bufferView = viewIndex,
|
||||
mimeType = bytesWithMime.mine,
|
||||
});
|
||||
|
||||
// add sampler
|
||||
var samplerIndex = gltf.samplers.Count;
|
||||
var sampler = TextureSamplerUtil.Export(texture);
|
||||
gltf.samplers.Add(sampler);
|
||||
|
||||
// add texture
|
||||
gltf.textures.Add(new glTFTexture
|
||||
{
|
||||
sampler = samplerIndex,
|
||||
source = imageIndex,
|
||||
});
|
||||
|
||||
return imageIndex;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,12 +0,0 @@
|
||||
fileFormatVersion: 2
|
||||
guid: eca1330a83e17a14eb99fc6ea1697922
|
||||
timeCreated: 1533533316
|
||||
licenseType: Free
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
@@ -1,5 +1,5 @@
|
||||
fileFormatVersion: 2
|
||||
guid: a4bd2e8f388fb204186d743f337ddb83
|
||||
guid: 2b2634da9b588264c8ea8a81578080b2
|
||||
folderAsset: yes
|
||||
DefaultImporter:
|
||||
externalObjects: {}
|
||||
52
Assets/UniGLTF/Runtime/UniGLTF/IO/TextureIO/ColorSpace.cs
Normal file
52
Assets/UniGLTF/Runtime/UniGLTF/IO/TextureIO/ColorSpace.cs
Normal file
@@ -0,0 +1,52 @@
|
||||
using System;
|
||||
using System.Linq;
|
||||
using UnityEngine;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public static class ColorSpace
|
||||
{
|
||||
public static RenderTextureReadWrite GetColorSpace(this glTFTextureTypes textureType)
|
||||
{
|
||||
switch (textureType)
|
||||
{
|
||||
case glTFTextureTypes.SRGB:
|
||||
return RenderTextureReadWrite.sRGB;
|
||||
case glTFTextureTypes.OcclusionMetallicRoughness:
|
||||
case glTFTextureTypes.Normal:
|
||||
return RenderTextureReadWrite.Linear;
|
||||
default:
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
|
||||
public static bool TryGetglTFTextureType(this glTF glTf, int textureIndex, out glTFTextureTypes textureType)
|
||||
{
|
||||
foreach (var material in glTf.materials)
|
||||
{
|
||||
var textureInfo = material.GetTextures().FirstOrDefault(x => (x != null) && x.index == textureIndex);
|
||||
if (textureInfo != null)
|
||||
{
|
||||
textureType = textureInfo.TextureType;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
// textureIndex is not used by Material.
|
||||
textureType = default;
|
||||
return false;
|
||||
}
|
||||
|
||||
public static RenderTextureReadWrite GetColorSpace(this glTF gltf, int textureIndex)
|
||||
{
|
||||
if (TryGetglTFTextureType(gltf, textureIndex, out glTFTextureTypes textureType))
|
||||
{
|
||||
return GetColorSpace(textureType);
|
||||
}
|
||||
else
|
||||
{
|
||||
return RenderTextureReadWrite.sRGB;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,5 +1,5 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 268e807d3ea7f0f45882d20bf318cf8b
|
||||
guid: 1a3edb24329fd454db97cac12f30c0d8
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
135
Assets/UniGLTF/Runtime/UniGLTF/IO/TextureIO/GetTextureParam.cs
Normal file
135
Assets/UniGLTF/Runtime/UniGLTF/IO/TextureIO/GetTextureParam.cs
Normal file
@@ -0,0 +1,135 @@
|
||||
using System;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
/// <summary>
|
||||
/// STANDARD(Pbr) texture = occlusion + metallic + smoothness
|
||||
/// </summary>
|
||||
public struct GetTextureParam
|
||||
{
|
||||
public const string NORMAL_PROP = "_BumpMap";
|
||||
public const string NORMAL_SUFFIX = ".normal";
|
||||
|
||||
public const string METALLIC_GLOSS_PROP = "_MetallicGlossMap";
|
||||
public const string OCCLUSION_PROP = "_OcclusionMap";
|
||||
public const string STANDARD_SUFFIX = ".standard";
|
||||
|
||||
public enum TextureTypes
|
||||
{
|
||||
sRGB,
|
||||
NormalMap,
|
||||
// Occlusion + Metallic + Smoothness
|
||||
StandardMap,
|
||||
Linear,
|
||||
}
|
||||
|
||||
public static string RemoveSuffix(string src)
|
||||
{
|
||||
if (src.EndsWith(NORMAL_SUFFIX))
|
||||
{
|
||||
return src.Substring(0, src.Length - NORMAL_SUFFIX.Length);
|
||||
}
|
||||
else if (src.EndsWith(STANDARD_SUFFIX))
|
||||
{
|
||||
return src.Substring(0, src.Length - STANDARD_SUFFIX.Length);
|
||||
}
|
||||
else
|
||||
{
|
||||
return src;
|
||||
}
|
||||
}
|
||||
|
||||
readonly string m_name;
|
||||
|
||||
public string GltflName => m_name;
|
||||
|
||||
public string ConvertedName
|
||||
{
|
||||
get
|
||||
{
|
||||
switch (TextureType)
|
||||
{
|
||||
case TextureTypes.StandardMap: return $"{m_name}{STANDARD_SUFFIX}";
|
||||
case TextureTypes.NormalMap: return $"{m_name}{NORMAL_SUFFIX}";
|
||||
default: return m_name;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public readonly TextureTypes TextureType;
|
||||
public readonly float MetallicFactor;
|
||||
public readonly float RoughnessFactor;
|
||||
public readonly ushort? Index0;
|
||||
public readonly ushort? Index1;
|
||||
public readonly ushort? Index2;
|
||||
public readonly ushort? Index3;
|
||||
public readonly ushort? Index4;
|
||||
public readonly ushort? Index5;
|
||||
|
||||
/// <summary>
|
||||
/// この種類は RGB チャンネルの組み換えが必用
|
||||
/// </summary>
|
||||
public bool ExtractConverted => TextureType == TextureTypes.StandardMap;
|
||||
|
||||
public GetTextureParam(string name, TextureTypes textureType, float metallicFactor, float roughnessFactor, int? i0, int? i1, int? i2, int? i3, int? i4, int? i5)
|
||||
{
|
||||
if (string.IsNullOrEmpty(name))
|
||||
{
|
||||
throw new ArgumentNullException();
|
||||
}
|
||||
m_name = name;
|
||||
|
||||
TextureType = textureType;
|
||||
MetallicFactor = metallicFactor;
|
||||
RoughnessFactor = roughnessFactor;
|
||||
Index0 = (ushort?)i0;
|
||||
Index1 = (ushort?)i1;
|
||||
Index2 = (ushort?)i2;
|
||||
Index3 = (ushort?)i3;
|
||||
Index4 = (ushort?)i4;
|
||||
Index5 = (ushort?)i5;
|
||||
}
|
||||
|
||||
public static GetTextureParam CreateSRGB(glTF gltf, int textureIndex)
|
||||
{
|
||||
var name = gltf.textures[textureIndex].name;
|
||||
return new GetTextureParam(name, TextureTypes.sRGB, default, default, textureIndex, default, default, default, default, default);
|
||||
}
|
||||
|
||||
public static GetTextureParam Create(glTF gltf, int index, string prop, float metallicFactor, float roughnessFactor)
|
||||
{
|
||||
switch (prop)
|
||||
{
|
||||
case NORMAL_PROP:
|
||||
return CreateNormal(gltf, index);
|
||||
|
||||
case OCCLUSION_PROP:
|
||||
case METALLIC_GLOSS_PROP:
|
||||
return CreateStandard(gltf, index, default, metallicFactor, roughnessFactor);
|
||||
|
||||
default:
|
||||
return CreateSRGB(gltf, index);
|
||||
}
|
||||
}
|
||||
|
||||
public static GetTextureParam CreateNormal(glTF gltf, int textureIndex)
|
||||
{
|
||||
var name = gltf.textures[textureIndex].name;
|
||||
return new GetTextureParam(name, TextureTypes.NormalMap, default, default, textureIndex, default, default, default, default, default);
|
||||
}
|
||||
|
||||
public static GetTextureParam CreateStandard(glTF gltf, int? metallicRoughnessTextureIndex, int? occlusionTextureIndex, float metallicFactor, float roughnessFactor)
|
||||
{
|
||||
string name = default;
|
||||
if (metallicRoughnessTextureIndex.HasValue)
|
||||
{
|
||||
name = gltf.textures[metallicRoughnessTextureIndex.Value].name;
|
||||
}
|
||||
else if (occlusionTextureIndex.HasValue)
|
||||
{
|
||||
name = gltf.textures[occlusionTextureIndex.Value].name;
|
||||
}
|
||||
return new GetTextureParam(name, TextureTypes.StandardMap, metallicFactor, roughnessFactor, metallicRoughnessTextureIndex, occlusionTextureIndex, default, default, default, default);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,94 @@
|
||||
using UnityEngine;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public static class GltfTextureExporter
|
||||
{
|
||||
|
||||
/// <summary>
|
||||
/// 画像のバイト列を得る
|
||||
/// </summary>
|
||||
/// <param name="bytes"></param>
|
||||
/// <param name="texture"></param>
|
||||
/// <returns></returns>
|
||||
static (byte[] bytes, string mine) GetBytesWithMime(Texture2D texture)
|
||||
{
|
||||
#if UNITY_EDITOR
|
||||
var path = UnityPath.FromAsset(texture);
|
||||
if (path.IsUnderAssetsFolder)
|
||||
{
|
||||
if (path.Extension == ".png")
|
||||
{
|
||||
return
|
||||
(
|
||||
System.IO.File.ReadAllBytes(path.FullPath),
|
||||
"image/png"
|
||||
);
|
||||
}
|
||||
if (path.Extension == ".jpg")
|
||||
{
|
||||
return
|
||||
(
|
||||
System.IO.File.ReadAllBytes(path.FullPath),
|
||||
"image/jpeg"
|
||||
);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
return
|
||||
(
|
||||
texture.EncodeToPNG(),
|
||||
"image/png"
|
||||
);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// gltf に texture を足す
|
||||
///
|
||||
/// * textures
|
||||
/// * samplers
|
||||
/// * images
|
||||
/// * bufferViews
|
||||
///
|
||||
/// を更新し、textures の index を返す
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="gltf"></param>
|
||||
/// <param name="bufferIndex"></param>
|
||||
/// <param name="texture"></param>
|
||||
/// <returns>gltf texture index</returns>
|
||||
public static int PushGltfTexture(this glTF gltf, int bufferIndex, Texture2D texture)
|
||||
{
|
||||
var bytesWithMime = GetBytesWithMime(texture);
|
||||
|
||||
// add view
|
||||
var view = gltf.buffers[bufferIndex].Append(bytesWithMime.bytes, glBufferTarget.NONE);
|
||||
var viewIndex = gltf.AddBufferView(view);
|
||||
|
||||
// add image
|
||||
var imageIndex = gltf.images.Count;
|
||||
gltf.images.Add(new glTFImage
|
||||
{
|
||||
name = GetTextureParam.RemoveSuffix(texture.name),
|
||||
bufferView = viewIndex,
|
||||
mimeType = bytesWithMime.mine,
|
||||
});
|
||||
|
||||
// add sampler
|
||||
var samplerIndex = gltf.samplers.Count;
|
||||
var sampler = TextureSamplerUtil.Export(texture);
|
||||
gltf.samplers.Add(sampler);
|
||||
|
||||
// add texture
|
||||
var textureIndex = gltf.textures.Count;
|
||||
gltf.textures.Add(new glTFTexture
|
||||
{
|
||||
sampler = samplerIndex,
|
||||
source = imageIndex,
|
||||
});
|
||||
|
||||
return textureIndex;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,5 +1,5 @@
|
||||
fileFormatVersion: 2
|
||||
guid: ae1f69c4441f3a74292499f75467c057
|
||||
guid: edc800243b783ea4392e1d916789c803
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
@@ -36,17 +36,15 @@ namespace UniGLTF
|
||||
//
|
||||
// texture from image(png etc) bytes
|
||||
//
|
||||
var textureType = TextureIO.GetglTFTextureType(gltf, textureIndex);
|
||||
var colorSpace = TextureIO.GetColorSpace(textureType);
|
||||
var isLinear = colorSpace == RenderTextureReadWrite.Linear;
|
||||
var sampler = gltf.GetSamplerFromTextureIndex(textureIndex);
|
||||
|
||||
var texture = new Texture2D(2, 2, TextureFormat.ARGB32, false, isLinear);
|
||||
var colorSpace = gltf.GetColorSpace(textureIndex);
|
||||
var texture = new Texture2D(2, 2, TextureFormat.ARGB32, false, colorSpace == RenderTextureReadWrite.Linear);
|
||||
texture.name = gltf.textures[textureIndex].name;
|
||||
if (imageBytes != null)
|
||||
{
|
||||
texture.LoadImage(imageBytes);
|
||||
}
|
||||
|
||||
var sampler = gltf.GetSamplerFromTextureIndex(textureIndex);
|
||||
if (sampler != null)
|
||||
{
|
||||
TextureSamplerUtil.SetSampler(texture, sampler);
|
||||
@@ -0,0 +1,47 @@
|
||||
using UnityEngine;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public static class NormalConverter
|
||||
{
|
||||
private static Material m_decoder;
|
||||
private static Material Decoder
|
||||
{
|
||||
get
|
||||
{
|
||||
if (m_decoder == null)
|
||||
{
|
||||
m_decoder = new Material(Shader.Find("UniGLTF/NormalMapDecoder"));
|
||||
}
|
||||
return m_decoder;
|
||||
}
|
||||
}
|
||||
|
||||
private static Material m_encoder;
|
||||
private static Material Encoder
|
||||
{
|
||||
get
|
||||
{
|
||||
if (m_encoder == null)
|
||||
{
|
||||
m_encoder = new Material(Shader.Find("UniGLTF/NormalMapEncoder"));
|
||||
}
|
||||
return m_encoder;
|
||||
}
|
||||
}
|
||||
|
||||
// GLTF data to Unity texture
|
||||
// ConvertToNormalValueFromRawColorWhenCompressionIsRequired
|
||||
public static Texture2D Import(Texture2D texture)
|
||||
{
|
||||
return TextureConverter.Convert(texture, glTFTextureTypes.Normal, null, Encoder);
|
||||
}
|
||||
|
||||
// Unity texture to GLTF data
|
||||
// ConvertToRawColorWhenNormalValueIsCompressed
|
||||
public static Texture2D Export(Texture texture)
|
||||
{
|
||||
return TextureConverter.Convert(texture, glTFTextureTypes.Normal, null, Decoder);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,5 +1,5 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 5c6170d9d89ac7f43b6860805e5e6214
|
||||
guid: 3640a6aad209c3f4d9178b078af8362f
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
@@ -0,0 +1,160 @@
|
||||
using System;
|
||||
using System.Linq;
|
||||
using UnityEngine;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
/// <summary>
|
||||
///
|
||||
/// * https://github.com/vrm-c/UniVRM/issues/781
|
||||
///
|
||||
/// Unity = glTF
|
||||
/// Occlusion: unity.g = glTF.r
|
||||
/// Roughness: unity.a = 1 - glTF.g * roughnessFactor
|
||||
/// Metallic : unity.r = glTF.b * metallicFactor
|
||||
///
|
||||
/// glTF = Unity
|
||||
/// Occlusion: glTF.r = unity.g
|
||||
/// Roughness: glTF.g = 1 - unity.a * smoothness
|
||||
/// Metallic : glTF.b = unity.r
|
||||
///
|
||||
/// </summary>
|
||||
public static class OcclusionMetallicRoughnessConverter
|
||||
{
|
||||
public static Texture2D Import(Texture2D metallicRoughnessTexture,
|
||||
float metallicFactor, float roughnessFactor, Texture2D occlusionTexture)
|
||||
{
|
||||
if (metallicRoughnessTexture != null && occlusionTexture != null)
|
||||
{
|
||||
if (metallicRoughnessTexture == occlusionTexture)
|
||||
{
|
||||
var copyMetallicRoughness = TextureConverter.CopyTexture(metallicRoughnessTexture, glTFTextureTypes.OcclusionMetallicRoughness, null);
|
||||
var metallicRoughnessPixels = copyMetallicRoughness.GetPixels32();
|
||||
for (int i = 0; i < metallicRoughnessPixels.Length; ++i)
|
||||
{
|
||||
metallicRoughnessPixels[i] = ImportPixel(metallicRoughnessPixels[i], metallicFactor, roughnessFactor, metallicRoughnessPixels[i]);
|
||||
}
|
||||
copyMetallicRoughness.SetPixels32(metallicRoughnessPixels);
|
||||
copyMetallicRoughness.Apply();
|
||||
copyMetallicRoughness.name = metallicRoughnessTexture.name;
|
||||
return copyMetallicRoughness;
|
||||
}
|
||||
else
|
||||
{
|
||||
var copyMetallicRoughness = TextureConverter.CopyTexture(metallicRoughnessTexture, glTFTextureTypes.OcclusionMetallicRoughness, null);
|
||||
var metallicRoughnessPixels = copyMetallicRoughness.GetPixels32();
|
||||
var copyOcclusion = TextureConverter.CopyTexture(occlusionTexture, glTFTextureTypes.OcclusionMetallicRoughness, null);
|
||||
var occlusionPixels = copyOcclusion.GetPixels32();
|
||||
if (metallicRoughnessPixels.Length != occlusionPixels.Length)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
for (int i = 0; i < metallicRoughnessPixels.Length; ++i)
|
||||
{
|
||||
metallicRoughnessPixels[i] = ImportPixel(metallicRoughnessPixels[i], metallicFactor, roughnessFactor, occlusionPixels[i]);
|
||||
}
|
||||
copyMetallicRoughness.SetPixels32(metallicRoughnessPixels);
|
||||
copyMetallicRoughness.Apply();
|
||||
copyMetallicRoughness.name = metallicRoughnessTexture.name;
|
||||
return copyMetallicRoughness;
|
||||
}
|
||||
}
|
||||
else if (metallicRoughnessTexture != null)
|
||||
{
|
||||
var copyTexture = TextureConverter.CopyTexture(metallicRoughnessTexture, glTFTextureTypes.OcclusionMetallicRoughness, null);
|
||||
copyTexture.SetPixels32(copyTexture.GetPixels32().Select(x => ImportPixel(x, metallicFactor, roughnessFactor, default)).ToArray());
|
||||
copyTexture.Apply();
|
||||
copyTexture.name = metallicRoughnessTexture.name;
|
||||
return copyTexture;
|
||||
}
|
||||
else if (occlusionTexture != null)
|
||||
{
|
||||
throw new NotImplementedException("occlusion only");
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new ArgumentNullException("no texture");
|
||||
}
|
||||
}
|
||||
|
||||
public static Color32 ImportPixel(Color32 metallicRoughness, float metallicFactor, float roughnessFactor, Color32 occlusion)
|
||||
{
|
||||
var dst = new Color32
|
||||
{
|
||||
r = (byte)(metallicRoughness.b * metallicFactor), // Metallic
|
||||
g = occlusion.r, // Occlusion
|
||||
b = 0, // not used
|
||||
a = (byte)(255 - metallicRoughness.g * roughnessFactor), // Roughness to Smoothness
|
||||
};
|
||||
|
||||
return dst;
|
||||
}
|
||||
|
||||
public static Texture2D Export(Texture metallicSmoothTexture, float smoothness, Texture occlusionTexture)
|
||||
{
|
||||
if (metallicSmoothTexture != null && occlusionTexture != null)
|
||||
{
|
||||
if (metallicSmoothTexture == occlusionTexture)
|
||||
{
|
||||
var copyTexture = TextureConverter.CopyTexture(metallicSmoothTexture, glTFTextureTypes.OcclusionMetallicRoughness, null);
|
||||
copyTexture.SetPixels32(copyTexture.GetPixels32().Select(x => ExportPixel(x, smoothness, x)).ToArray());
|
||||
copyTexture.Apply();
|
||||
copyTexture.name = metallicSmoothTexture.name;
|
||||
return copyTexture;
|
||||
}
|
||||
else
|
||||
{
|
||||
var copyMetallicSmooth = TextureConverter.CopyTexture(metallicSmoothTexture, glTFTextureTypes.OcclusionMetallicRoughness, null);
|
||||
var metallicSmoothPixels = copyMetallicSmooth.GetPixels32();
|
||||
var copyOcclusion = TextureConverter.CopyTexture(occlusionTexture, glTFTextureTypes.OcclusionMetallicRoughness, null);
|
||||
var occlusionPixels = copyOcclusion.GetPixels32();
|
||||
if (metallicSmoothPixels.Length != occlusionPixels.Length)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
for (int i = 0; i < metallicSmoothPixels.Length; ++i)
|
||||
{
|
||||
metallicSmoothPixels[i] = ExportPixel(metallicSmoothPixels[i], smoothness, occlusionPixels[i]);
|
||||
}
|
||||
copyMetallicSmooth.SetPixels32(metallicSmoothPixels);
|
||||
copyMetallicSmooth.Apply();
|
||||
copyMetallicSmooth.name = metallicSmoothTexture.name;
|
||||
return copyMetallicSmooth;
|
||||
}
|
||||
}
|
||||
else if (metallicSmoothTexture)
|
||||
{
|
||||
var copyTexture = TextureConverter.CopyTexture(metallicSmoothTexture, glTFTextureTypes.OcclusionMetallicRoughness, null);
|
||||
copyTexture.SetPixels32(copyTexture.GetPixels32().Select(x => ExportPixel(x, smoothness, default)).ToArray());
|
||||
copyTexture.Apply();
|
||||
copyTexture.name = metallicSmoothTexture.name;
|
||||
return copyTexture;
|
||||
}
|
||||
else if (occlusionTexture)
|
||||
{
|
||||
var copyTexture = TextureConverter.CopyTexture(occlusionTexture, glTFTextureTypes.OcclusionMetallicRoughness, null);
|
||||
copyTexture.SetPixels32(copyTexture.GetPixels32().Select(x => ExportPixel(default, smoothness, x)).ToArray());
|
||||
copyTexture.Apply();
|
||||
copyTexture.name = occlusionTexture.name;
|
||||
return copyTexture;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new ArgumentNullException();
|
||||
}
|
||||
}
|
||||
|
||||
public static Color32 ExportPixel(Color32 metallicSmooth, float smoothness, Color32 occlusion)
|
||||
{
|
||||
var dst = new Color32
|
||||
{
|
||||
r = occlusion.g, // Occlusion
|
||||
g = (byte)(255 - metallicSmooth.a * smoothness), // Roughness from Smoothness
|
||||
b = metallicSmooth.r, // Metallic
|
||||
a = 255, // not used
|
||||
};
|
||||
|
||||
return dst;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 9de35f7c2673d5d48b84d494e71f25ff
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
@@ -14,9 +14,9 @@ namespace UniGLTF
|
||||
{
|
||||
public delegate Color32 ColorConversion(Color32 color);
|
||||
|
||||
public static Texture2D Convert(Texture2D texture, glTFTextureTypes textureType, ColorConversion colorConversion, Material convertMaterial)
|
||||
public static Texture2D Convert(Texture texture, glTFTextureTypes textureType, ColorConversion colorConversion, Material convertMaterial)
|
||||
{
|
||||
var copyTexture = CopyTexture(texture, TextureIO.GetColorSpace(textureType), convertMaterial);
|
||||
var copyTexture = CopyTexture(texture, textureType, convertMaterial);
|
||||
if (colorConversion != null)
|
||||
{
|
||||
copyTexture.SetPixels32(copyTexture.GetPixels32().Select(x => colorConversion(x)).ToArray());
|
||||
@@ -126,10 +126,10 @@ namespace UniGLTF
|
||||
}
|
||||
#endif
|
||||
|
||||
public static Texture2D CopyTexture(Texture src, RenderTextureReadWrite colorSpace, Material material)
|
||||
public static Texture2D CopyTexture(Texture src, glTFTextureTypes textureType, Material material)
|
||||
{
|
||||
Texture2D dst = null;
|
||||
|
||||
RenderTextureReadWrite colorSpace = textureType.GetColorSpace();
|
||||
var renderTexture = new RenderTexture(src.width, src.height, 0, RenderTextureFormat.ARGB32, colorSpace);
|
||||
|
||||
using (var scope = new ColorSpaceScope(colorSpace))
|
||||
@@ -1,5 +1,5 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 0342907cb8901f44b8792016ac152fcd
|
||||
guid: 843bfd183520d064ea63b4716d26b7cc
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
224
Assets/UniGLTF/Runtime/UniGLTF/IO/TextureIO/TextureExporter.cs
Normal file
224
Assets/UniGLTF/Runtime/UniGLTF/IO/TextureIO/TextureExporter.cs
Normal file
@@ -0,0 +1,224 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using UnityEngine;
|
||||
using System.Reflection;
|
||||
#if UNITY_EDITOR
|
||||
using UnityEditor;
|
||||
#endif
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
/// <summary>
|
||||
/// glTF にエクスポートする Texture2D を蓄えて index を確定させる
|
||||
/// </summary>
|
||||
public class TextureExporter
|
||||
{
|
||||
struct ExportKey
|
||||
{
|
||||
public readonly Texture Src;
|
||||
public readonly glTFTextureTypes TextureType;
|
||||
|
||||
public ExportKey(Texture src, glTFTextureTypes type)
|
||||
{
|
||||
if (src == null)
|
||||
{
|
||||
throw new ArgumentNullException();
|
||||
}
|
||||
Src = src;
|
||||
TextureType = type;
|
||||
}
|
||||
}
|
||||
Dictionary<ExportKey, int> m_exportMap = new Dictionary<ExportKey, int>();
|
||||
|
||||
/// <summary>
|
||||
/// Export する Texture2D のリスト。これが gltf.textures になる
|
||||
/// </summary>
|
||||
/// <typeparam name="Texture2D"></typeparam>
|
||||
/// <returns></returns>
|
||||
public readonly List<Texture2D> Exported = new List<Texture2D>();
|
||||
|
||||
/// <summary>
|
||||
/// Texture の export index を得る
|
||||
/// </summary>
|
||||
/// <param name="src"></param>
|
||||
/// <param name="textureType"></param>
|
||||
/// <returns></returns>
|
||||
public int GetTextureIndex(Texture src, glTFTextureTypes textureType)
|
||||
{
|
||||
if (src == null)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
return m_exportMap[new ExportKey(src, textureType)];
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// TextureImporter.maxTextureSize が元のテクスチャーより小さいか否かの判定
|
||||
/// </summary>
|
||||
/// <param name="src"></param>
|
||||
/// <returns></returns>
|
||||
static bool CopyIfMaxTextureSizeIsSmaller(Texture src)
|
||||
{
|
||||
#if UNITY_EDITOR
|
||||
var textureImporter = AssetImporter.GetAtPath(UnityPath.FromAsset(src).Value) as TextureImporter;
|
||||
var getSizeMethod = typeof(TextureImporter).GetMethod("GetWidthAndHeight", BindingFlags.NonPublic | BindingFlags.Instance);
|
||||
if (textureImporter != null && getSizeMethod != null)
|
||||
{
|
||||
var args = new object[2] { 0, 0 };
|
||||
getSizeMethod.Invoke(textureImporter, args);
|
||||
var originalWidth = (int)args[0];
|
||||
var originalHeight = (int)args[1];
|
||||
var originalSize = Mathf.Max(originalWidth, originalHeight);
|
||||
if (textureImporter.maxTextureSize < originalSize)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 元の Asset が存在して、 TextureImporter に設定された画像サイズが小さくない
|
||||
/// </summary>
|
||||
/// <param name="src"></param>
|
||||
/// <param name="texture2D"></param>
|
||||
/// <returns></returns>
|
||||
static bool UseAsset(Texture2D texture2D)
|
||||
{
|
||||
#if UNITY_EDITOR
|
||||
if (texture2D != null && !string.IsNullOrEmpty(UnityEditor.AssetDatabase.GetAssetPath(texture2D)))
|
||||
{
|
||||
if (CopyIfMaxTextureSizeIsSmaller(texture2D))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// sRGBなテクスチャーを処理し、index を確定させる
|
||||
/// </summary>
|
||||
/// <param name="src"></param>
|
||||
/// <returns></returns>
|
||||
public int ExportSRGB(Texture src)
|
||||
{
|
||||
if (src == null)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
// cache
|
||||
if (m_exportMap.TryGetValue(new ExportKey(src, glTFTextureTypes.SRGB), out var index))
|
||||
{
|
||||
return index;
|
||||
}
|
||||
|
||||
// get Texture2D
|
||||
index = Exported.Count;
|
||||
var texture2D = src as Texture2D;
|
||||
if (UseAsset(texture2D))
|
||||
{
|
||||
// do nothing
|
||||
}
|
||||
else
|
||||
{
|
||||
texture2D = TextureConverter.CopyTexture(src, glTFTextureTypes.SRGB, null);
|
||||
}
|
||||
Exported.Add(texture2D);
|
||||
m_exportMap.Add(new ExportKey(src, glTFTextureTypes.SRGB), index);
|
||||
|
||||
return index;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Linearなテクスチャーを処理し、index を確定させる
|
||||
/// </summary>
|
||||
/// <param name="src"></param>
|
||||
/// <returns></returns>
|
||||
public int ExportLinear(Texture src)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Standard の Metallic, Smoothness, Occlusion をまとめ、index を確定させる
|
||||
/// </summary>
|
||||
/// <param name="metallicSmoothTexture"></param>
|
||||
/// <param name="smoothness"></param>
|
||||
/// <param name="occlusionTexture"></param>
|
||||
/// <returns></returns>
|
||||
public int ExportMetallicSmoothnessOcclusion(Texture metallicSmoothTexture, float smoothness, Texture occlusionTexture)
|
||||
{
|
||||
if (metallicSmoothTexture == null && occlusionTexture == null)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
// cache
|
||||
if (m_exportMap.TryGetValue(new ExportKey(metallicSmoothTexture, glTFTextureTypes.OcclusionMetallicRoughness), out var index))
|
||||
{
|
||||
return index;
|
||||
}
|
||||
if (m_exportMap.TryGetValue(new ExportKey(occlusionTexture, glTFTextureTypes.OcclusionMetallicRoughness), out index))
|
||||
{
|
||||
return index;
|
||||
}
|
||||
|
||||
//
|
||||
// Unity と glTF で互換性が無いので必ず変換が必用
|
||||
//
|
||||
index = Exported.Count;
|
||||
var texture2D = OcclusionMetallicRoughnessConverter.Export(metallicSmoothTexture, smoothness, occlusionTexture);
|
||||
|
||||
Exported.Add(texture2D);
|
||||
m_exportMap.Add(new ExportKey(metallicSmoothTexture, glTFTextureTypes.OcclusionMetallicRoughness), index);
|
||||
if (occlusionTexture != metallicSmoothTexture && occlusionTexture != null)
|
||||
{
|
||||
m_exportMap.Add(new ExportKey(occlusionTexture, glTFTextureTypes.OcclusionMetallicRoughness), index);
|
||||
}
|
||||
|
||||
return index;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Normal のテクスチャを変換し index を確定させる
|
||||
/// </summary>
|
||||
/// <param name="normalTexture"></param>
|
||||
/// <returns></returns>
|
||||
public int ExportNormal(Texture src)
|
||||
{
|
||||
if (src == null)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
// cache
|
||||
if (m_exportMap.TryGetValue(new ExportKey(src, glTFTextureTypes.Normal), out var index))
|
||||
{
|
||||
return index;
|
||||
}
|
||||
|
||||
// get Texture2D
|
||||
index = Exported.Count;
|
||||
var texture2D = src as Texture2D;
|
||||
if (UseAsset(texture2D))
|
||||
{
|
||||
// EditorAsset を使うので変換不要
|
||||
}
|
||||
else
|
||||
{
|
||||
// 後で Bitmap を使うために変換する
|
||||
texture2D = NormalConverter.Export(src);
|
||||
}
|
||||
|
||||
Exported.Add(texture2D);
|
||||
m_exportMap.Add(new ExportKey(src, glTFTextureTypes.Normal), index);
|
||||
|
||||
return index;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 65fdfff6cc4b1e14a882259e903fc830
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
@@ -46,24 +46,26 @@ namespace UniGLTF
|
||||
public delegate Task<Texture2D> GetTextureAsyncFunc(IAwaitCaller awaitCaller, glTF gltf, GetTextureParam param);
|
||||
public class TextureFactory : IDisposable
|
||||
{
|
||||
Dictionary<string, Texture2D> m_externalMap;
|
||||
public readonly Dictionary<string, Texture2D> ExternalMap;
|
||||
|
||||
public bool TryGetExternal(GetTextureParam param, bool used, out Texture2D external)
|
||||
{
|
||||
if (param.Index0.HasValue && m_externalMap != null)
|
||||
if (param.Index0.HasValue && ExternalMap != null)
|
||||
{
|
||||
var cacheName = param.ConvertedName;
|
||||
if (param.TextureType == GetTextureParam.NORMAL_PROP)
|
||||
if (param.TextureType == GetTextureParam.TextureTypes.NormalMap)
|
||||
{
|
||||
cacheName = param.GltflName;
|
||||
}
|
||||
|
||||
if (m_externalMap.TryGetValue(cacheName, out external))
|
||||
{
|
||||
if (!m_textureCache.ContainsKey(cacheName))
|
||||
if (m_textureCache.TryGetValue(cacheName, out TextureLoadInfo normalInfo))
|
||||
{
|
||||
m_textureCache.Add(cacheName, new TextureLoadInfo(external, used, true));
|
||||
external = normalInfo.Texture;
|
||||
return true;
|
||||
}
|
||||
return external;
|
||||
}
|
||||
if (ExternalMap.TryGetValue(cacheName, out external))
|
||||
{
|
||||
m_textureCache.Add(cacheName, new TextureLoadInfo(external, used, true));
|
||||
return true;
|
||||
}
|
||||
}
|
||||
external = default;
|
||||
@@ -78,7 +80,7 @@ namespace UniGLTF
|
||||
LoadTextureAsync = loadTextureAsync;
|
||||
if (externalMap != null)
|
||||
{
|
||||
m_externalMap = externalMap
|
||||
ExternalMap = externalMap
|
||||
.Select(kv => (kv.Item1, kv.Item2 as Texture2D))
|
||||
.Where(kv => kv.Item2 != null)
|
||||
.ToDictionary(kv => kv.Item1, kv => kv.Item2);
|
||||
@@ -164,31 +166,25 @@ namespace UniGLTF
|
||||
|
||||
switch (param.TextureType)
|
||||
{
|
||||
case GetTextureParam.NORMAL_PROP:
|
||||
case GetTextureParam.TextureTypes.NormalMap:
|
||||
{
|
||||
var baseTexture = await GetOrCreateBaseTexture(awaitCaller, gltf, param.Index0.Value, false);
|
||||
var converted = new NormalConverter().GetImportTexture(baseTexture.Texture);
|
||||
var converted = NormalConverter.Import(baseTexture.Texture);
|
||||
converted.name = param.ConvertedName;
|
||||
var info = new TextureLoadInfo(converted, true, false);
|
||||
m_textureCache.Add(converted.name, info);
|
||||
return info.Texture;
|
||||
}
|
||||
|
||||
case GetTextureParam.METALLIC_GLOSS_PROP:
|
||||
{
|
||||
// Bake roughnessFactor values into a texture.
|
||||
var baseTexture = await GetOrCreateBaseTexture(awaitCaller, gltf, param.Index0.Value, false);
|
||||
var converted = new MetallicRoughnessConverter(param.MetallicFactor).GetImportTexture(baseTexture.Texture);
|
||||
converted.name = param.ConvertedName;
|
||||
var info = new TextureLoadInfo(converted, true, false);
|
||||
m_textureCache.Add(converted.name, info);
|
||||
return info.Texture;
|
||||
}
|
||||
|
||||
case GetTextureParam.OCCLUSION_PROP:
|
||||
case GetTextureParam.TextureTypes.StandardMap:
|
||||
{
|
||||
var baseTexture = await GetOrCreateBaseTexture(awaitCaller, gltf, param.Index0.Value, false);
|
||||
var converted = new OcclusionConverter().GetImportTexture(baseTexture.Texture);
|
||||
TextureLoadInfo occlusionBaseTexture = default;
|
||||
if (param.Index1.HasValue)
|
||||
{
|
||||
occlusionBaseTexture = await GetOrCreateBaseTexture(awaitCaller, gltf, param.Index1.Value, false);
|
||||
}
|
||||
var converted = OcclusionMetallicRoughnessConverter.Import(baseTexture.Texture, param.MetallicFactor, param.RoughnessFactor, occlusionBaseTexture.Texture);
|
||||
converted.name = param.ConvertedName;
|
||||
var info = new TextureLoadInfo(converted, true, false);
|
||||
m_textureCache.Add(converted.name, info);
|
||||
@@ -1,5 +1,5 @@
|
||||
fileFormatVersion: 2
|
||||
guid: f3929edbda61f9346906bfab93411b98
|
||||
guid: 62f23c5ca623a9f4083c25a63b2c82af
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
@@ -1,126 +0,0 @@
|
||||
using System;
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public struct GetTextureParam
|
||||
{
|
||||
public const string NORMAL_PROP = "_BumpMap";
|
||||
public const string NORMAL_SUFFIX = ".normal";
|
||||
public const string METALLIC_GLOSS_PROP = "_MetallicGlossMap";
|
||||
public const string METALLIC_GLOSS_SUFFIX = ".metallicRoughness";
|
||||
public const string OCCLUSION_PROP = "_OcclusionMap";
|
||||
public const string OCCLUSION_SUFFIX = ".occlusion";
|
||||
|
||||
public static string RemoveSuffix(string src)
|
||||
{
|
||||
if (src.EndsWith(NORMAL_SUFFIX))
|
||||
{
|
||||
return src.Substring(0, src.Length - NORMAL_SUFFIX.Length);
|
||||
}
|
||||
else if (src.EndsWith(METALLIC_GLOSS_SUFFIX))
|
||||
{
|
||||
return src.Substring(0, src.Length - METALLIC_GLOSS_SUFFIX.Length);
|
||||
}
|
||||
else if (src.EndsWith(OCCLUSION_SUFFIX))
|
||||
{
|
||||
return src.Substring(0, src.Length - OCCLUSION_SUFFIX.Length);
|
||||
}
|
||||
else
|
||||
{
|
||||
return src;
|
||||
}
|
||||
}
|
||||
|
||||
readonly string m_name;
|
||||
|
||||
public string GltflName => m_name;
|
||||
|
||||
public string ConvertedName
|
||||
{
|
||||
get
|
||||
{
|
||||
switch (TextureType)
|
||||
{
|
||||
case METALLIC_GLOSS_PROP: return $"{m_name}{METALLIC_GLOSS_SUFFIX}";
|
||||
case OCCLUSION_PROP: return $"{m_name}{OCCLUSION_SUFFIX}";
|
||||
case NORMAL_PROP: return $"{m_name}{NORMAL_SUFFIX}";
|
||||
default: return m_name;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public readonly string TextureType;
|
||||
public readonly float MetallicFactor;
|
||||
public readonly ushort? Index0;
|
||||
public readonly ushort? Index1;
|
||||
public readonly ushort? Index2;
|
||||
public readonly ushort? Index3;
|
||||
public readonly ushort? Index4;
|
||||
public readonly ushort? Index5;
|
||||
|
||||
/// <summary>
|
||||
/// この2種類は変換済みをExtract
|
||||
/// </summary>
|
||||
public bool ExtractConverted => TextureType == OCCLUSION_PROP || TextureType == METALLIC_GLOSS_PROP;
|
||||
|
||||
public GetTextureParam(string name, string textureType, float metallicFactor, int i0, int i1, int i2, int i3, int i4, int i5)
|
||||
{
|
||||
if (string.IsNullOrEmpty(name))
|
||||
{
|
||||
throw new ArgumentNullException();
|
||||
}
|
||||
m_name = name;
|
||||
|
||||
TextureType = textureType;
|
||||
MetallicFactor = metallicFactor;
|
||||
Index0 = (ushort)i0;
|
||||
Index1 = (ushort)i1;
|
||||
Index2 = (ushort)i2;
|
||||
Index3 = (ushort)i3;
|
||||
Index4 = (ushort)i4;
|
||||
Index5 = (ushort)i5;
|
||||
}
|
||||
|
||||
public static GetTextureParam Create(glTF gltf, int textureIndex)
|
||||
{
|
||||
var name = gltf.textures[textureIndex].name;
|
||||
return new GetTextureParam(name, default, default, textureIndex, default, default, default, default, default);
|
||||
}
|
||||
|
||||
public static GetTextureParam Create(glTF gltf, int index, string prop)
|
||||
{
|
||||
switch (prop)
|
||||
{
|
||||
case NORMAL_PROP:
|
||||
return CreateNormal(gltf, index);
|
||||
|
||||
case OCCLUSION_PROP:
|
||||
return CreateOcclusion(gltf, index);
|
||||
|
||||
case METALLIC_GLOSS_PROP:
|
||||
return CreateMetallic(gltf, index, 1);
|
||||
|
||||
default:
|
||||
return Create(gltf, index);
|
||||
}
|
||||
}
|
||||
|
||||
public static GetTextureParam CreateNormal(glTF gltf, int textureIndex)
|
||||
{
|
||||
var name = gltf.textures[textureIndex].name;
|
||||
return new GetTextureParam(name, NORMAL_PROP, default, textureIndex, default, default, default, default, default);
|
||||
}
|
||||
|
||||
public static GetTextureParam CreateMetallic(glTF gltf, int textureIndex, float metallicFactor)
|
||||
{
|
||||
var name = gltf.textures[textureIndex].name;
|
||||
return new GetTextureParam(name, METALLIC_GLOSS_PROP, metallicFactor, textureIndex, default, default, default, default, default);
|
||||
}
|
||||
|
||||
public static GetTextureParam CreateOcclusion(glTF gltf, int textureIndex)
|
||||
{
|
||||
var name = gltf.textures[textureIndex].name;
|
||||
return new GetTextureParam(name, OCCLUSION_PROP, default, textureIndex, default, default, default, default, default);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -47,35 +47,13 @@ namespace UniGLTF
|
||||
private set;
|
||||
}
|
||||
|
||||
public TextureExportManager TextureManager;
|
||||
public TextureExporter TextureManager;
|
||||
|
||||
protected virtual IMaterialExporter CreateMaterialExporter()
|
||||
{
|
||||
return new MaterialExporter();
|
||||
}
|
||||
|
||||
private ITextureExporter _textureExporter;
|
||||
public ITextureExporter TextureExporter
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_textureExporter != null)
|
||||
{
|
||||
return _textureExporter;
|
||||
}
|
||||
else
|
||||
{
|
||||
_textureExporter = new TextureIO();
|
||||
return _textureExporter;
|
||||
}
|
||||
}
|
||||
set
|
||||
{
|
||||
_textureExporter = value;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// このエクスポーターがサポートするExtension
|
||||
/// </summary>
|
||||
@@ -201,22 +179,21 @@ namespace UniGLTF
|
||||
|
||||
#region Materials and Textures
|
||||
Materials = Nodes.SelectMany(x => x.GetSharedMaterials()).Where(x => x != null).Distinct().ToList();
|
||||
var unityTextures = Materials.SelectMany(x => TextureExporter.GetTextures(x)).Where(x => x.texture != null).Distinct().ToList();
|
||||
|
||||
TextureManager = new TextureExportManager(unityTextures.Select(x => x.texture));
|
||||
TextureManager = new TextureExporter();
|
||||
|
||||
var materialExporter = CreateMaterialExporter();
|
||||
glTF.materials = Materials.Select(x => materialExporter.ExportMaterial(x, TextureManager)).ToList();
|
||||
|
||||
for (int i = 0; i < unityTextures.Count; ++i)
|
||||
for (int i = 0; i < TextureManager.Exported.Count; ++i)
|
||||
{
|
||||
var unityTexture = unityTextures[i];
|
||||
TextureExporter.ExportTexture(glTF, bufferIndex, TextureManager.GetExportTexture(i), unityTexture.textureType);
|
||||
var unityTexture = TextureManager.Exported[i];
|
||||
glTF.PushGltfTexture(bufferIndex, unityTexture);
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region Meshes
|
||||
var unityMeshes = MeshWithRenderer.FromNodes(Nodes).Where(x=> x.Mesh.vertices.Any()).ToList();
|
||||
var unityMeshes = MeshWithRenderer.FromNodes(Nodes).Where(x => x.Mesh.vertices.Any()).ToList();
|
||||
|
||||
MeshBlendShapeIndexMap = new Dictionary<Mesh, Dictionary<int, int>>();
|
||||
foreach (var (mesh, gltfMesh, blendShapeIndexMap) in MeshExporter.ExportMeshes(
|
||||
|
||||
@@ -19,7 +19,7 @@ namespace UniGLTF
|
||||
filterMode = FilterMode.Bilinear,
|
||||
};
|
||||
|
||||
var textureManager = new TextureExportManager(new Texture[] { tex0 });
|
||||
var textureManager = new TextureExporter();
|
||||
var srcMaterial = new Material(Shader.Find("Standard"));
|
||||
|
||||
var offset = new Vector2(0.3f, 0.2f);
|
||||
@@ -255,7 +255,7 @@ namespace UniGLTF
|
||||
material.SetColor("_EmissionColor", new Color(0, 1, 2, 1));
|
||||
material.EnableKeyword("_EMISSION");
|
||||
var materialExporter = new MaterialExporter();
|
||||
var textureExportManager = new TextureExportManager(new Texture[] { });
|
||||
var textureExportManager = new TextureExporter();
|
||||
var gltfMaterial = materialExporter.ExportMaterial(material, textureExportManager);
|
||||
|
||||
Assert.AreEqual(gltfMaterial.emissiveFactor, new float[] { 0, 0.5f, 1 });
|
||||
|
||||
@@ -14,7 +14,7 @@ namespace UniGLTF
|
||||
wrapMode = TextureWrapMode.Clamp,
|
||||
filterMode = FilterMode.Trilinear,
|
||||
};
|
||||
var textureManager = new TextureExportManager(new Texture[] {tex0});
|
||||
var textureManager = new TextureExporter();
|
||||
|
||||
var material = new Material(Shader.Find("Standard"));
|
||||
material.mainTexture = tex0;
|
||||
@@ -22,7 +22,7 @@ namespace UniGLTF
|
||||
var materialExporter = new MaterialExporter();
|
||||
materialExporter.ExportMaterial(material, textureManager);
|
||||
|
||||
var convTex0 = textureManager.GetExportTexture(0);
|
||||
var convTex0 = textureManager.Exported[0];
|
||||
var sampler = TextureSamplerUtil.Export(convTex0);
|
||||
|
||||
Assert.AreEqual(glWrap.CLAMP_TO_EDGE, sampler.wrapS);
|
||||
@@ -39,9 +39,8 @@ namespace UniGLTF
|
||||
{
|
||||
{
|
||||
var smoothness = 1.0f;
|
||||
var conv = new MetallicRoughnessConverter(smoothness);
|
||||
Assert.That(
|
||||
conv.Export(new Color32(255, 255, 255, 255)),
|
||||
OcclusionMetallicRoughnessConverter.ExportPixel(new Color32(255, 255, 255, 255), smoothness, default),
|
||||
// r <- 0 : (Unused)
|
||||
// g <- 0 : ((1 - src.a(as float) * smoothness) ^ 2)(as uint8)
|
||||
// b <- 255 : Same metallic (src.r)
|
||||
@@ -51,21 +50,19 @@ namespace UniGLTF
|
||||
|
||||
{
|
||||
var smoothness = 0.5f;
|
||||
var conv = new MetallicRoughnessConverter(smoothness);
|
||||
Assert.That(
|
||||
conv.Export(new Color32(255, 255, 255, 255)),
|
||||
OcclusionMetallicRoughnessConverter.ExportPixel(new Color32(255, 255, 255, 255), smoothness, default),
|
||||
// r <- 0 : (Unused)
|
||||
// g <- 63 : ((1 - src.a(as float) * smoothness) ^ 2)(as uint8)
|
||||
// b <- 255 : Same metallic (src.r)
|
||||
// a <- 255 : (Unused)
|
||||
Is.EqualTo(new Color32(0, 63, 255, 255)));
|
||||
Is.EqualTo(new Color32(0, 127, 255, 255)));
|
||||
}
|
||||
|
||||
{
|
||||
var smoothness = 0.0f;
|
||||
var conv = new MetallicRoughnessConverter(smoothness);
|
||||
Assert.That(
|
||||
conv.Export(new Color32(255, 255, 255, 255)),
|
||||
OcclusionMetallicRoughnessConverter.ExportPixel(new Color32(255, 255, 255, 255), smoothness, default),
|
||||
// r <- 0 : (Unused)
|
||||
// g <- 255 : ((1 - src.a(as float) * smoothness) ^ 2)(as uint8)
|
||||
// b <- 255 : Same metallic (src.r)
|
||||
@@ -79,9 +76,8 @@ namespace UniGLTF
|
||||
{
|
||||
{
|
||||
var roughnessFactor = 1.0f;
|
||||
var conv = new MetallicRoughnessConverter(roughnessFactor);
|
||||
Assert.That(
|
||||
conv.Import(new Color32(255, 255, 255, 255)),
|
||||
OcclusionMetallicRoughnessConverter.ImportPixel(new Color32(255, 255, 255, 255), 1.0f, roughnessFactor, default),
|
||||
// r <- 255 : Same metallic (src.r)
|
||||
// g <- 0 : (Unused)
|
||||
// b <- 0 : (Unused)
|
||||
@@ -91,33 +87,30 @@ namespace UniGLTF
|
||||
|
||||
{
|
||||
var roughnessFactor = 1.0f;
|
||||
var conv = new MetallicRoughnessConverter(roughnessFactor);
|
||||
Assert.That(
|
||||
conv.Import(new Color32(255, 63, 255, 255)),
|
||||
OcclusionMetallicRoughnessConverter.ImportPixel(new Color32(255, 128, 255, 255), 1.0f, roughnessFactor, default),
|
||||
// r <- 255 : Same metallic (src.r)
|
||||
// g <- 0 : (Unused)
|
||||
// b <- 0 : (Unused)
|
||||
// a <- 128 : ((1 - sqrt(src.g(as float) * roughnessFactor)))(as uint8)
|
||||
Is.EqualTo(new Color32(255, 0, 0, 128))); // smoothness 0.5 * src.a 1.0
|
||||
Is.EqualTo(new Color32(255, 0, 0, 127))); // smoothness 0.5 * src.a 1.0
|
||||
}
|
||||
|
||||
{
|
||||
var roughnessFactor = 0.5f;
|
||||
var conv = new MetallicRoughnessConverter(roughnessFactor);
|
||||
Assert.That(
|
||||
conv.Import(new Color32(255, 255, 255, 255)),
|
||||
OcclusionMetallicRoughnessConverter.ImportPixel(new Color32(255, 255, 255, 255), 1.0f, roughnessFactor, default),
|
||||
// r <- 255 : Same metallic (src.r)
|
||||
// g <- 0 : (Unused)
|
||||
// b <- 0 : (Unused)
|
||||
// a <- 74 : ((1 - sqrt(src.g(as float) * roughnessFactor)))(as uint8)
|
||||
Is.EqualTo(new Color32(255, 0, 0, 74)));
|
||||
Is.EqualTo(new Color32(255, 0, 0, 127)));
|
||||
}
|
||||
|
||||
{
|
||||
var roughnessFactor = 0.0f;
|
||||
var conv = new MetallicRoughnessConverter(roughnessFactor);
|
||||
Assert.That(
|
||||
conv.Import(new Color32(255, 255, 255, 255)),
|
||||
OcclusionMetallicRoughnessConverter.ImportPixel(new Color32(255, 255, 255, 255), 1.0f, roughnessFactor, default),
|
||||
// r <- 255 : Same metallic (src.r)
|
||||
// g <- 0 : (Unused)
|
||||
// b <- 0 : (Unused)
|
||||
|
||||
@@ -10,7 +10,7 @@ namespace VRM.Samples
|
||||
{
|
||||
var material = Resources.Load<Material>(resourceName);
|
||||
var exporter = new VRMMaterialExporter();
|
||||
var textureManager = new UniGLTF.TextureExportManager(null);
|
||||
var textureManager = new UniGLTF.TextureExporter();
|
||||
var exported = exporter.ExportMaterial(material, textureManager);
|
||||
|
||||
// parse glTFExtensionExport to glTFExtensionImport
|
||||
|
||||
@@ -4,6 +4,7 @@ using UnityEngine;
|
||||
using UniGLTF;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
|
||||
namespace VRM
|
||||
{
|
||||
@@ -58,14 +59,24 @@ namespace VRM
|
||||
var parser = new GltfParser();
|
||||
parser.ParseGlb(File.ReadAllBytes(path));
|
||||
|
||||
Action<IEnumerable<string>> onCompleted = _ =>
|
||||
Action<IEnumerable<string>> onCompleted = texturePaths =>
|
||||
{
|
||||
//
|
||||
// after textures imported
|
||||
//
|
||||
var map = texturePaths.Select(x =>
|
||||
{
|
||||
var texture = AssetDatabase.LoadAssetAtPath(x, typeof(Texture2D));
|
||||
return (texture.name, texture);
|
||||
}).ToArray();
|
||||
|
||||
using (var context = new VRMImporterContext(parser))
|
||||
{
|
||||
var editor = new VRMEditorImporterContext(context, prefabPath);
|
||||
foreach (var textureInfo in new VRMTextureEnumerator(context.VRM).Enumerate(parser.GLTF))
|
||||
{
|
||||
TextureImporterConfigurator.Configure(textureInfo, map.ToDictionary(x => x.name, x => x.texture as Texture2D));
|
||||
}
|
||||
context.Load();
|
||||
editor.SaveAsAsset();
|
||||
}
|
||||
|
||||
@@ -25,7 +25,14 @@ namespace VRM
|
||||
var ext = Path.GetExtension(path).ToLower();
|
||||
if (ext == ".vrm")
|
||||
{
|
||||
ImportVrm(UnityPath.FromUnityPath(path));
|
||||
try
|
||||
{
|
||||
ImportVrm(UnityPath.FromUnityPath(path));
|
||||
}
|
||||
catch (VRMImporterContext.NotVrm0Exception)
|
||||
{
|
||||
// is not vrm0
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -49,9 +56,14 @@ namespace VRM
|
||||
var texture = AssetDatabase.LoadAssetAtPath(x, typeof(Texture2D));
|
||||
return (texture.name, texture);
|
||||
}).ToArray();
|
||||
|
||||
using (var context = new VRMImporterContext(parser, null, map))
|
||||
{
|
||||
var editor = new VRMEditorImporterContext(context, prefabPath);
|
||||
foreach (var textureInfo in new VRMTextureEnumerator(context.VRM).Enumerate(parser.GLTF))
|
||||
{
|
||||
TextureImporterConfigurator.Configure(textureInfo, map.ToDictionary(x => x.name, x => x.texture as Texture2D));
|
||||
}
|
||||
context.Load();
|
||||
editor.SaveAsAsset();
|
||||
}
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using UniGLTF;
|
||||
using UniJSON;
|
||||
@@ -113,7 +112,7 @@ namespace VRM
|
||||
VRM.meta.title = meta.Title;
|
||||
if (meta.Thumbnail != null)
|
||||
{
|
||||
VRM.meta.texture = TextureExporter.ExportTexture(glTF, glTF.buffers.Count - 1, meta.Thumbnail, glTFTextureTypes.Unknown);
|
||||
VRM.meta.texture = glTF.PushGltfTexture(glTF.buffers.Count - 1, meta.Thumbnail);
|
||||
}
|
||||
|
||||
VRM.meta.licenseType = meta.LicenseType;
|
||||
@@ -138,7 +137,7 @@ namespace VRM
|
||||
VRM.meta.title = meta.Title;
|
||||
if (meta.Thumbnail != null)
|
||||
{
|
||||
VRM.meta.texture = TextureExporter.ExportTexture(glTF, glTF.buffers.Count - 1, meta.Thumbnail, glTFTextureTypes.Unknown);
|
||||
VRM.meta.texture = TextureManager.ExportSRGB(meta.Thumbnail);
|
||||
}
|
||||
|
||||
// ussage permission
|
||||
@@ -201,7 +200,7 @@ namespace VRM
|
||||
// materials
|
||||
foreach (var m in Materials)
|
||||
{
|
||||
VRM.materialProperties.Add(VRMMaterialExporter.CreateFromMaterial(m, TextureManager.Textures));
|
||||
VRM.materialProperties.Add(VRMMaterialExporter.CreateFromMaterial(m, TextureManager));
|
||||
}
|
||||
|
||||
// Serialize VRM
|
||||
|
||||
@@ -10,6 +10,12 @@ namespace VRM
|
||||
{
|
||||
public class VRMImporterContext : ImporterContext
|
||||
{
|
||||
public class NotVrm0Exception : Exception
|
||||
{
|
||||
public NotVrm0Exception()
|
||||
{ }
|
||||
}
|
||||
|
||||
public VRM.glTF_VRM_extensions VRM { get; private set; }
|
||||
|
||||
public VRMImporterContext(GltfParser parser,
|
||||
@@ -25,7 +31,7 @@ namespace VRM
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new KeyNotFoundException("not vrm0");
|
||||
throw new NotVrm0Exception();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -292,7 +298,7 @@ namespace VRM
|
||||
meta.Title = gltfMeta.title;
|
||||
if (gltfMeta.texture >= 0)
|
||||
{
|
||||
meta.Thumbnail = await TextureFactory.GetTextureAsync(awaitCaller, GLTF, GetTextureParam.Create(GLTF, gltfMeta.texture));
|
||||
meta.Thumbnail = await TextureFactory.GetTextureAsync(awaitCaller, GLTF, GetTextureParam.CreateSRGB(GLTF, gltfMeta.texture));
|
||||
}
|
||||
meta.AllowedUser = gltfMeta.allowedUser;
|
||||
meta.ViolentUssage = gltfMeta.violentUssage;
|
||||
|
||||
@@ -107,7 +107,7 @@ namespace VRM
|
||||
// "Queue",
|
||||
};
|
||||
|
||||
public static glTF_VRM_Material CreateFromMaterial(Material m, List<Texture> textures)
|
||||
public static glTF_VRM_Material CreateFromMaterial(Material m, TextureExporter textureExporter)
|
||||
{
|
||||
var material = new glTF_VRM_Material
|
||||
{
|
||||
@@ -160,7 +160,10 @@ namespace VRM
|
||||
var texture = m.GetTexture(kv.Key);
|
||||
if (texture != null)
|
||||
{
|
||||
var value = textures.IndexOf(texture);
|
||||
var value = kv.Key == "_BumpMap"
|
||||
? textureExporter.ExportNormal(texture)
|
||||
: textureExporter.ExportSRGB(texture)
|
||||
;
|
||||
if (value == -1)
|
||||
{
|
||||
Debug.LogFormat("not found {0}", texture.name);
|
||||
|
||||
@@ -73,7 +73,7 @@ namespace VRM
|
||||
}
|
||||
foreach (var kv in item.textureProperties)
|
||||
{
|
||||
var param = GetTextureParam.Create(gltf, kv.Value, kv.Key);
|
||||
var param = GetTextureParam.Create(gltf, kv.Value, kv.Key, 1, 1);
|
||||
var texture = await getTexture(awaitCaller, gltf, param);
|
||||
if (texture != null)
|
||||
{
|
||||
|
||||
@@ -22,7 +22,7 @@ namespace VRM
|
||||
foreach (var kv in vrmMaterial.textureProperties)
|
||||
{
|
||||
// SRGB color or normalmap
|
||||
yield return GetTextureParam.Create(gltf, kv.Value, kv.Key);
|
||||
yield return GetTextureParam.Create(gltf, kv.Value, kv.Key, default, default);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -38,7 +38,7 @@ namespace VRM
|
||||
// thumbnail
|
||||
if (m_vrm.meta != null && m_vrm.meta.texture != -1)
|
||||
{
|
||||
yield return GetTextureParam.Create(gltf, m_vrm.meta.texture);
|
||||
yield return GetTextureParam.CreateSRGB(gltf, m_vrm.meta.texture);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user