mirror of
https://github.com/vrm-c/UniVRM.git
synced 2026-05-23 19:36:18 -05:00
TextureFactory manipulate ExternalObjectMap
This commit is contained in:
parent
b4f71fed84
commit
bdadbc9f80
|
|
@ -25,28 +25,25 @@ namespace UniGLTF
|
|||
parser.ParsePath(ctx.assetPath);
|
||||
|
||||
// Build Unity Model
|
||||
var context = new ImporterContext(parser);
|
||||
var context = new ImporterContext(parser, GetExternalObjectMap()
|
||||
.Select(kv => new KeyValuePair<string, UnityEngine.Object>(kv.Key.name, kv.Value)));
|
||||
context.Load();
|
||||
context.ShowMeshes();
|
||||
|
||||
// Texture
|
||||
var externalTextures = this.GetExternalUnityObjects<UnityEngine.Texture2D>();
|
||||
foreach (var texture in context.Textures)
|
||||
foreach (var info in context.TextureFactory.Textures)
|
||||
{
|
||||
if (texture == null)
|
||||
{
|
||||
throw new Exception();
|
||||
}
|
||||
|
||||
if (!externalTextures.ContainsValue(texture))
|
||||
if (!info.UseExternal)
|
||||
{
|
||||
var texture = info.Texture;
|
||||
ctx.AddObjectToAsset(texture.name, texture);
|
||||
}
|
||||
}
|
||||
|
||||
// Material
|
||||
var externalMaterials = this.GetExternalUnityObjects<UnityEngine.Material>();
|
||||
foreach (var material in context.Materials)
|
||||
foreach (var material in context.MaterialFactory.Materials)
|
||||
{
|
||||
if (material == null)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -19,19 +19,15 @@ namespace UniGLTF
|
|||
|
||||
EditorGUILayout.BeginHorizontal();
|
||||
EditorGUILayout.PrefixLabel("Materials And Textures");
|
||||
GUI.enabled = !(importer.GetExternalUnityObjects<UnityEngine.Material>().Any()
|
||||
&& importer.GetExternalUnityObjects<UnityEngine.Texture2D>().Any());
|
||||
if (GUILayout.Button("Extract"))
|
||||
{
|
||||
importer.ExtractMaterialsAndTextures();
|
||||
}
|
||||
GUI.enabled = !GUI.enabled;
|
||||
if (GUILayout.Button("Clear"))
|
||||
{
|
||||
importer.ClearExternalObjects<UnityEngine.Material>();
|
||||
importer.ClearExternalObjects<UnityEngine.Texture2D>();
|
||||
}
|
||||
GUI.enabled = true;
|
||||
EditorGUILayout.EndHorizontal();
|
||||
|
||||
// ObjectMap
|
||||
|
|
|
|||
|
|
@ -37,16 +37,14 @@ namespace UniGLTF
|
|||
|
||||
MaterialFactory m_materialFactory;
|
||||
public MaterialFactory MaterialFactory => m_materialFactory;
|
||||
public IEnumerable<Material> Materials => m_materialFactory.Materials;
|
||||
|
||||
TextureFactory m_textureFactory;
|
||||
public TextureFactory TextureFactory => m_textureFactory;
|
||||
public IEnumerable<Texture2D> Textures => m_textureFactory.Textures;
|
||||
|
||||
public ImporterContext(GltfParser parser)
|
||||
public ImporterContext(GltfParser parser, IEnumerable<KeyValuePair<string, UnityEngine.Object>> externalObjectMap = null)
|
||||
{
|
||||
m_parser = parser;
|
||||
m_textureFactory = new TextureFactory(GLTF, Storage);
|
||||
m_textureFactory = new TextureFactory(GLTF, Storage, externalObjectMap);
|
||||
m_materialFactory = new MaterialFactory(GLTF, Storage);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ namespace UniGLTF
|
|||
{
|
||||
if (getTexture == null)
|
||||
{
|
||||
getTexture = _ => Awaitable.FromResult<Texture2D>(null);
|
||||
getTexture = _ => Awaitable.FromResult<Texture2D>(default);
|
||||
}
|
||||
|
||||
var material = MaterialFactory.CreateMaterial(i, src, ShaderName);
|
||||
|
|
|
|||
|
|
@ -1,23 +1,43 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using UniGLTF.AltTask;
|
||||
using UnityEditor;
|
||||
using UnityEngine;
|
||||
using System.Linq;
|
||||
#if UNITY_EDITOR
|
||||
using UnityEditor;
|
||||
#endif
|
||||
|
||||
namespace UniGLTF
|
||||
{
|
||||
public struct TextureLoadInfo
|
||||
{
|
||||
public readonly Texture2D Texture;
|
||||
public readonly bool UseExternal;
|
||||
|
||||
public TextureLoadInfo(Texture2D texture, bool useExternal)
|
||||
{
|
||||
Texture = texture;
|
||||
UseExternal = useExternal;
|
||||
}
|
||||
}
|
||||
|
||||
public delegate Awaitable<Texture2D> GetTextureAsyncFunc(GetTextureParam param);
|
||||
public class TextureFactory : IDisposable
|
||||
{
|
||||
glTF m_gltf;
|
||||
IStorage m_storage;
|
||||
Dictionary<string, Texture2D> m_externalMap;
|
||||
|
||||
public UnityPath ImageBaseDir { get; set; }
|
||||
|
||||
public TextureFactory(glTF gltf, IStorage storage)
|
||||
public TextureFactory(glTF gltf, IStorage storage, IEnumerable<KeyValuePair<string, UnityEngine.Object>> externalMap)
|
||||
{
|
||||
m_gltf = gltf;
|
||||
m_storage = storage;
|
||||
m_externalMap = externalMap
|
||||
.Select(kv => (kv.Key, kv.Value as Texture2D))
|
||||
.Where(kv => kv.Item2 != null)
|
||||
.ToDictionary(kv => kv.Item1, kv => kv.Item2);
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
|
|
@ -32,22 +52,42 @@ namespace UniGLTF
|
|||
{
|
||||
foreach (var kv in m_textureCache)
|
||||
{
|
||||
yield return kv.Value;
|
||||
yield return kv.Value.Texture;
|
||||
}
|
||||
}
|
||||
|
||||
Dictionary<GetTextureParam, Texture2D> m_textureCache = new Dictionary<GetTextureParam, Texture2D>();
|
||||
public IEnumerable<Texture2D> Textures => m_textureCache.Values;
|
||||
Dictionary<GetTextureParam, TextureLoadInfo> m_textureCache = new Dictionary<GetTextureParam, TextureLoadInfo>();
|
||||
|
||||
public virtual Awaitable<Texture2D> LoadTextureAsync(int index)
|
||||
public IEnumerable<TextureLoadInfo> Textures => m_textureCache.Values;
|
||||
|
||||
public virtual async Awaitable<TextureLoadInfo> LoadTextureAsync(int index)
|
||||
{
|
||||
#if UNIGLTF_USE_WEBREQUEST_TEXTURELOADER
|
||||
return UnityWebRequestTextureLoader.LoadTextureAsync(index);
|
||||
#else
|
||||
return GltfTextureLoader.LoadTextureAsync(m_gltf, m_storage, index);
|
||||
var texture = await GltfTextureLoader.LoadTextureAsync(m_gltf, m_storage, index);
|
||||
return new TextureLoadInfo(texture, false);
|
||||
#endif
|
||||
}
|
||||
|
||||
public bool TryGetExternal(GetTextureParam param, out Texture2D external)
|
||||
{
|
||||
if (param.Index0.HasValue && m_externalMap != null)
|
||||
{
|
||||
var gltfTexture = m_gltf.textures[param.Index0.Value];
|
||||
m_gltf.GetImageBytes(m_storage, gltfTexture.source, out string textureName);
|
||||
|
||||
if (m_externalMap.TryGetValue(textureName, out external))
|
||||
{
|
||||
Debug.Log($"use external: {textureName}");
|
||||
m_textureCache.Add(param, new TextureLoadInfo(external, true));
|
||||
return external;
|
||||
}
|
||||
}
|
||||
external = default;
|
||||
return false;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// テクスチャーをロード、必要であれば変換して返す。
|
||||
/// 同じものはキャッシュを返す
|
||||
|
|
@ -58,17 +98,21 @@ namespace UniGLTF
|
|||
/// <returns></returns>
|
||||
public async Awaitable<Texture2D> GetTextureAsync(GetTextureParam param)
|
||||
{
|
||||
if (m_textureCache.TryGetValue(param, out Texture2D texture))
|
||||
if (m_textureCache.TryGetValue(param, out TextureLoadInfo info))
|
||||
{
|
||||
return texture;
|
||||
return info.Texture;
|
||||
}
|
||||
if (TryGetExternal(param, out Texture2D external))
|
||||
{
|
||||
return external;
|
||||
}
|
||||
|
||||
{
|
||||
var defaultParam = GetTextureParam.Create(param.Index0.Value);
|
||||
if (!m_textureCache.TryGetValue(defaultParam, out texture))
|
||||
if (!m_textureCache.TryGetValue(defaultParam, out info))
|
||||
{
|
||||
texture = await LoadTextureAsync(param.Index0.Value);
|
||||
m_textureCache.Add(defaultParam, texture);
|
||||
info = await LoadTextureAsync(param.Index0.Value);
|
||||
m_textureCache.Add(defaultParam, info);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -78,49 +122,52 @@ namespace UniGLTF
|
|||
{
|
||||
if (Application.isPlaying)
|
||||
{
|
||||
var converted = new NormalConverter().GetImportTexture(texture);
|
||||
m_textureCache.Add(param, converted);
|
||||
var converted = new NormalConverter().GetImportTexture(info.Texture);
|
||||
converted.name = $"{converted.name}.{GetTextureParam.NORMAL_PROP}";
|
||||
return converted;
|
||||
info = new TextureLoadInfo(converted, false);
|
||||
m_textureCache.Add(param, info);
|
||||
return info.Texture;
|
||||
}
|
||||
else
|
||||
{
|
||||
#if UNITY_EDITOR
|
||||
var textureAssetPath = AssetDatabase.GetAssetPath(texture);
|
||||
var textureAssetPath = AssetDatabase.GetAssetPath(info.Texture);
|
||||
if (!string.IsNullOrEmpty(textureAssetPath))
|
||||
{
|
||||
TextureIO.MarkTextureAssetAsNormalMap(textureAssetPath);
|
||||
texture.name = $"{texture.name}.{GetTextureParam.NORMAL_PROP}";
|
||||
info.Texture.name = $"{info.Texture.name}.{GetTextureParam.NORMAL_PROP}";
|
||||
}
|
||||
else
|
||||
{
|
||||
Debug.LogWarningFormat("no asset for {0}", texture);
|
||||
Debug.LogWarningFormat("no asset for {0}", info);
|
||||
}
|
||||
#endif
|
||||
m_textureCache.Add(param, texture);
|
||||
return texture;
|
||||
m_textureCache.Add(param, info);
|
||||
return info.Texture;
|
||||
}
|
||||
}
|
||||
|
||||
case GetTextureParam.METALLIC_GLOSS_PROP:
|
||||
{
|
||||
// Bake roughnessFactor values into a texture.
|
||||
var converted = new MetallicRoughnessConverter(param.MetallicFactor).GetImportTexture(texture);
|
||||
var converted = new MetallicRoughnessConverter(param.MetallicFactor).GetImportTexture(info.Texture);
|
||||
converted.name = $"{converted.name}.{GetTextureParam.METALLIC_GLOSS_PROP}";
|
||||
m_textureCache.Add(param, converted);
|
||||
return converted;
|
||||
info = new TextureLoadInfo(converted, false);
|
||||
m_textureCache.Add(param, info);
|
||||
return info.Texture;
|
||||
}
|
||||
|
||||
case GetTextureParam.OCCLUSION_PROP:
|
||||
{
|
||||
var converted = new OcclusionConverter().GetImportTexture(texture);
|
||||
var converted = new OcclusionConverter().GetImportTexture(info.Texture);
|
||||
converted.name = $"{converted.name}.{GetTextureParam.OCCLUSION_PROP}";
|
||||
m_textureCache.Add(param, converted);
|
||||
return converted;
|
||||
info = new TextureLoadInfo(converted, false);
|
||||
m_textureCache.Add(param, info);
|
||||
return info.Texture;
|
||||
}
|
||||
|
||||
default:
|
||||
return texture;
|
||||
return info.Texture;
|
||||
}
|
||||
|
||||
throw new NotImplementedException();
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user