diff --git a/Assets/VRM/UniGLTF/Scripts/IO/MeshExporter.cs b/Assets/VRM/UniGLTF/Scripts/IO/MeshExporter.cs
index 9969922fe..4e9fd8ed7 100644
--- a/Assets/VRM/UniGLTF/Scripts/IO/MeshExporter.cs
+++ b/Assets/VRM/UniGLTF/Scripts/IO/MeshExporter.cs
@@ -22,17 +22,72 @@ namespace UniGLTF
public bool IsRendererActive;
public bool Skinned;
+ ///
+ /// Mesh に頂点カラーが含まれているか。
+ /// 含まれている場合にマテリアルは Unlit.VColorMultiply になっているか?
+ ///
public enum VertexColorState
{
- // 存在しない
+ // VColorが存在しない
None,
- // 存在して使用している
+ // VColorが存在して使用している(UnlitはすべてVColorMultiply)
ExistsAndIsUsed,
- // 存在するが使用していない
+ // VColorが存在するが使用していない(UnlitはすべてVColorNone。もしくはUnlitが存在しない)
ExistsButNotUsed,
+ // VColorが存在して、Unlit.Multiply と Unlit.NotMultiply が混在している。 Unlit.NotMultiply を MToon か Standardに変更した方がよい
+ ExistsAndMixed,
}
public VertexColorState VertexColor;
+ static bool MaterialUseVertexColor(Material m)
+ {
+ if (m.shader.name != UniGLTF.UniUnlit.Utils.ShaderName)
+ {
+ return false;
+ }
+ if (UniGLTF.UniUnlit.Utils.GetVColBlendMode(m) != UniGLTF.UniUnlit.UniUnlitVertexColorBlendOp.Multiply)
+ {
+ return false;
+ }
+ return true;
+ }
+
+ public static VertexColorState DetectVertexColor(Mesh mesh, Material[] materials)
+ {
+ if (mesh != null && mesh.colors != null && mesh.colors.Length == mesh.vertexCount)
+ {
+ // mesh が 頂点カラーを保持している
+ VertexColorState? state = default;
+ if (materials != null)
+ {
+ foreach (var m in materials)
+ {
+ var currentState = MaterialUseVertexColor(m)
+ ? UniGLTF.MeshExportInfo.VertexColorState.ExistsAndIsUsed
+ : UniGLTF.MeshExportInfo.VertexColorState.ExistsButNotUsed
+ ;
+ if (state.HasValue)
+ {
+ if (state.Value != currentState)
+ {
+ state = UniGLTF.MeshExportInfo.VertexColorState.ExistsAndMixed;
+ break;
+ }
+ }
+ else
+ {
+ state = currentState;
+ }
+ }
+ }
+ return state.GetValueOrDefault(VertexColorState.None);
+ }
+ else
+ {
+ return VertexColorState.None;
+ }
+ }
+
public int VertexCount;
///
@@ -92,15 +147,14 @@ namespace UniGLTF
var uvAccessorIndex = gltf.ExtendBufferAndGetAccessorIndex(bufferIndex, mesh.uv.Select(y => y.ReverseUV()).ToArray(), glBufferTarget.ARRAY_BUFFER);
var colorAccessorIndex = -1;
- if (mesh.colors != null && mesh.colors.Length == mesh.vertexCount)
+
+ var vColorState = MeshExportInfo.DetectVertexColor(mesh, materials);
+ if (vColorState == MeshExportInfo.VertexColorState.ExistsAndIsUsed // VColor使っている
+ || vColorState == MeshExportInfo.VertexColorState.ExistsAndMixed // VColorを使っているところと使っていないところが混在(とりあえずExportする)
+ )
{
- // この Mesh が 頂点カラーを保持していて
- if (materials.Any(x => x.shader.name == UniGLTF.UniUnlit.Utils.ShaderName
- && UniGLTF.UniUnlit.Utils.GetVColBlendMode(x) == UniUnlit.UniUnlitVertexColorBlendOp.Multiply))
- {
- // UniUnlit で Multiply 設定になっている
- colorAccessorIndex = gltf.ExtendBufferAndGetAccessorIndex(bufferIndex, mesh.colors, glBufferTarget.ARRAY_BUFFER);
- }
+ // UniUnlit で Multiply 設定になっている
+ colorAccessorIndex = gltf.ExtendBufferAndGetAccessorIndex(bufferIndex, mesh.colors, glBufferTarget.ARRAY_BUFFER);
}
var boneweights = mesh.boneWeights;
diff --git a/Assets/VRM/UniVRM/Editor/Format/VRMExportMeshes.cs b/Assets/VRM/UniVRM/Editor/Format/VRMExportMeshes.cs
index eadb742b0..9f46c9f56 100644
--- a/Assets/VRM/UniVRM/Editor/Format/VRMExportMeshes.cs
+++ b/Assets/VRM/UniVRM/Editor/Format/VRMExportMeshes.cs
@@ -62,19 +62,6 @@ namespace VRM
List m_validations = new List();
public IEnumerable Validations => m_validations;
- static bool MaterialUseVertexColor(Material m)
- {
- if (m.shader.name != UniGLTF.UniUnlit.Utils.ShaderName)
- {
- return false;
- }
- if (UniGLTF.UniUnlit.Utils.GetVColBlendMode(m) != UniGLTF.UniUnlit.UniUnlitVertexColorBlendOp.Multiply)
- {
- return false;
- }
- return true;
- }
-
public static void CalcMeshSize(ref UniGLTF.MeshExportInfo info,
string relativePath, VRMExportSettings settings, IReadOnlyList clips)
{
@@ -193,17 +180,7 @@ namespace VRM
return false;
}
- if (info.Mesh.colors != null && info.Mesh.colors.Length == info.Mesh.vertexCount)
- {
- if (renderer.sharedMaterials.Any(x => MaterialUseVertexColor(x)))
- {
- info.VertexColor = UniGLTF.MeshExportInfo.VertexColorState.ExistsAndIsUsed;
- }
- else
- {
- info.VertexColor = UniGLTF.MeshExportInfo.VertexColorState.ExistsButNotUsed;
- }
- }
+ info.VertexColor = UniGLTF.MeshExportInfo.DetectVertexColor(info.Mesh, info.Renderer.sharedMaterials);
var relativePath = UniGLTF.UnityExtensions.RelativePathFrom(renderer.transform, root.transform);
CalcMeshSize(ref info, relativePath, settings, clips);