protected override void Init()
        {
            base.Init();

            this._root = new GLTFRoot
            {
                Accessors = new List <Accessor>(),
                Asset     = new Asset
                {
                    Version   = "2.0",
                    Generator = "paper",
                },
                Buffers     = new List <GLTF.Schema.Buffer>(),
                BufferViews = new List <BufferView>(),
                Animations  = new List <GLTF.Schema.Animation>(),
            };

            _buffer   = new GLTF.Schema.Buffer();
            _bufferId = new BufferId
            {
                Id   = _root.Buffers.Count,
                Root = _root
            };
            _root.Buffers.Add(_buffer);
        }
        /// <summary>
        /// Create a GLTFExporter that exports out a transform
        /// </summary>
        /// <param name="rootTransforms">Root transform of object to export</param>
        public GLTFSceneExporter(Transform[] rootTransforms)
        {
            _rootTransforms = rootTransforms;
            _root           = new GLTFRoot {
                Accessors = new List <Accessor>(),
                Asset     = new Asset {
                    Version = "2.0"
                },
                Buffers     = new List <GLTF.Schema.Buffer>(),
                BufferViews = new List <BufferView>(),
                Images      = new List <Image>(),
                Materials   = new List <GLTF.Schema.Material>(),
                Meshes      = new List <GLTF.Schema.Mesh>(),
                Nodes       = new List <Node>(),
                Samplers    = new List <Sampler>(),
                Scenes      = new List <Scene>(),
                Textures    = new List <GLTF.Schema.Texture>(),
            };

            _images    = new List <Texture2D>();
            _materials = new List <UnityEngine.Material>();
            _textures  = new List <UnityEngine.Texture>();

            _buffer   = new GLTF.Schema.Buffer();
            _bufferId = new BufferId {
                Id   = _root.Buffers.Count,
                Root = _root
            };
            _root.Buffers.Add(_buffer);
        }
예제 #3
0
        /// <summary>
        /// Load the remote URI data into a byte array.
        /// </summary>
        protected virtual IEnumerator LoadBuffer(string sourceUri, GLTF.Schema.Buffer buffer, int bufferIndex)
        {
            if (buffer.Uri != null)
            {
                Stream bufferStream = null;
                var    uri          = buffer.Uri;

                Regex regex = new Regex(Base64StringInitializer);
                Match match = regex.Match(uri);
                if (match.Success)
                {
                    string base64String   = uri.Substring(match.Length);
                    byte[] base64ByteData = Convert.FromBase64String(base64String);
                    bufferStream = new MemoryStream(base64ByteData, 0, base64ByteData.Length, false, true);
                }
                else if (_loadType == LoadType.Uri)
                {
                    var www = UnityWebRequest.Get(Path.Combine(sourceUri, uri));

                    yield return(www.Send());

                    bufferStream = new MemoryStream(www.downloadHandler.data, 0, www.downloadHandler.data.Length, false, true);
                }
                else if (_loadType == LoadType.Stream)
                {
                    var pathToLoad = Path.Combine(sourceUri, uri);
                    bufferStream = File.OpenRead(pathToLoad);
                }

                _assetCache.BufferCache[bufferIndex] = new BufferCacheData()
                {
                    Stream = bufferStream
                };
            }
        }
예제 #4
0
        protected override void Init()
        {
            base.Init();

            this._root = new GLTFRoot
            {
                Accessors = new List <Accessor>(),
                Asset     = new Asset
                {
                    Version    = "2.0",
                    Generator  = "paper",
                    Extensions = new Dictionary <string, IExtension>(),
                },
                Buffers     = new List <GLTF.Schema.Buffer>(),
                BufferViews = new List <BufferView>(),
                Meshes      = new List <GLTF.Schema.Mesh>()
            };

            _root.Asset.Extensions.Add(CoordinateSystemExtensionFactory.EXTENSION_NAME, new CoordinateSystemExtension(CoordinateSystem.leftHand.ToString(), 1.0f));

            _buffer   = new GLTF.Schema.Buffer();
            _bufferId = new BufferId
            {
                Id   = _root.Buffers.Count,
                Root = _root
            };
            _root.Buffers.Add(_buffer);
        }
예제 #5
0
        // todo undo
#if !WINDOWS_UWP
        IEnumerator Start()
        {
            var     fullPath0 = Application.streamingAssetsPath + Path.DirectorySeparatorChar + asset0Path;
            ILoader loader0   = new FileLoader(URIHelper.GetDirectoryName(fullPath0));

            var     fullPath1 = Application.streamingAssetsPath + Path.DirectorySeparatorChar + asset1Path;
            ILoader loader1   = new FileLoader(URIHelper.GetDirectoryName(fullPath1));

            yield return(loader0.LoadStream(Path.GetFileName(asset0Path)));

            var asset0Stream = loader0.LoadedStream;
            var asset0Root   = GLTFParser.ParseJson(asset0Stream);

            yield return(loader1.LoadStream(Path.GetFileName(asset1Path)));

            var asset1Stream = loader1.LoadedStream;
            var asset1Root   = GLTFParser.ParseJson(asset1Stream);

            string newPath = "../../" + URIHelper.GetDirectoryName(asset0Path);

            int previousBufferCount  = asset1Root.Buffers.Count;
            int previousImageCount   = asset1Root.Images.Count;
            int previousSceneCounter = asset1Root.Scenes.Count;

            GLTFHelpers.MergeGLTF(asset1Root, asset0Root);

            for (int i = previousBufferCount; i < asset1Root.Buffers.Count; ++i)
            {
                GLTF.Schema.Buffer buffer = asset1Root.Buffers[i];
                if (!URIHelper.IsBase64Uri(buffer.Uri))
                {
                    buffer.Uri = newPath + buffer.Uri;
                }
            }

            for (int i = previousImageCount; i < asset1Root.Images.Count; ++i)
            {
                Image image = asset1Root.Images[i];
                if (!URIHelper.IsBase64Uri(image.Uri))
                {
                    image.Uri = newPath + image.Uri;
                }
            }

            foreach (NodeId node in asset1Root.Scenes[asset0Root.Scene.Id + previousSceneCounter].Nodes)
            {
                node.Value.Translation.X += 5f;
                asset1Root.Scene.Value.Nodes.Add(node);
            }
            GLTFSceneImporter importer = new GLTFSceneImporter(
                asset1Root,
                loader1
                );

            importer.MaximumLod = MaximumLod;

            yield return(importer.LoadScene(-1, Multithreaded));
        }
 protected virtual void LoadBuffer(string sourceUri, GLTF.Schema.Buffer buffer, int bufferIndex)
 {
     if (buffer.Uri != null)
     {
         byte[] bufferData = null;
         var    uri        = buffer.Uri;
         var    bufferPath = Path.Combine(sourceUri, uri);
         bufferData = File.ReadAllBytes(bufferPath);
         _assetCache.BufferCache[bufferIndex] = bufferData;
     }
 }
        public void Finish()
        {
            var prefixStr = Config.GeneratorName;
            for (var i = Config.GeneratorName.Length; i < 24; i += 1)
            {
                prefixStr += " ";
            }
            var prefix = Encoding.ASCII.GetBytes(prefixStr);
            var uri = name + ".bin";
            var fp = Path.Combine(ExporterSettings.Export.folder, uri);
            var bufferId = new BufferId { Id = 0, Root = root };
            var outputFile = new FileStream(fp, FileMode.Create);
            int offset = prefix.Length;

            using (var binWriter = new BinaryWriter(outputFile)) {
                binWriter.Write(prefix);

                foreach (var bufferView in _bufferViews)
                {
                    int length = 0;

                    if (bufferView.byteBuffer != null)
                    {
                        length = bufferView.byteBuffer.Length;
                        binWriter.Write(bufferView.byteBuffer);
                    } else if (bufferView.streamBuffer != null)
                    {
                        length = (int)bufferView.streamBuffer.Length;
                        binWriter.Write(bufferView.streamBuffer.ToArray());
                    }

                    bufferView.view.ByteLength = length;
                    bufferView.view.ByteOffset = offset;
                    bufferView.view.Buffer = bufferId;

                    offset += length;
                }

                binWriter.Flush();
            }

            var buffer = new GLTF.Schema.Buffer();
            buffer.ByteLength = offset;
            buffer.Uri = uri;
            root.Buffers = new List<GLTF.Schema.Buffer> { buffer };

            using (var writer = File.CreateText(path))
            {
                root.Serialize(writer);
            }
        }
        protected override void Init()
        {
            base.Init();

            _root = new GLTFRoot
            {
                Accessors = new List <Accessor>(),
                Asset     = new Asset
                {
                    Version   = "2.0",
                    Generator = "paper",
                },
                Buffers     = new List <GLTF.Schema.Buffer>(),
                BufferViews = new List <BufferView>()
                {
                    new BufferView {
                        Buffer = new BufferId()
                        {
                            Id   = 0,
                            Root = _root,
                        },
                        ByteOffset = 0,
                        ByteLength = 0,
                    }
                },
                Nodes  = new List <Node>(),
                Scenes = new List <Scene>()
                {
                    new Scene()
                    {
                        Nodes = new List <NodeId>(),
                    }
                },
                Animations = new List <GLTF.Schema.Animation>(),
            };

            _buffer   = new GLTF.Schema.Buffer();
            _bufferId = new BufferId
            {
                Id   = _root.Buffers.Count,
                Root = _root
            };
            _root.Buffers.Add(_buffer);
        }
예제 #9
0
        /// <summary>
        /// Load the remote URI data into a byte array.
        /// </summary>
        protected virtual IEnumerator LoadBuffer(string sourceUri, GLTF.Schema.Buffer buffer, int bufferIndex)
        {
            if (buffer.Uri != null)
            {
                byte[] bufferData = null;
                var    uri        = buffer.Uri;

                Regex regex = new Regex(Base64StringInitializer);
                Match match = regex.Match(uri);
                if (match.Success)
                {
                    var base64Data = uri.Substring(match.Length);
                    bufferData = Convert.FromBase64String(base64Data);
                }
                else if (_loadType == LoadType.Uri)
                {
                    var www = UnityWebRequest.Get(Path.Combine(sourceUri, uri));

#if UNITY_2017_2_OR_NEWER
                    yield return(www.SendWebRequest());
#else
                    yield return(www.Send());
#endif

                    bufferData = www.downloadHandler.data;
                }
                else if (_loadType == LoadType.Stream)
                {
                    var pathToLoad = Path.Combine(sourceUri, uri);
                    var file       = File.OpenRead(pathToLoad);
                    bufferData = new byte[buffer.ByteLength];
                    file.Read(bufferData, 0, buffer.ByteLength);
#if !WINDOWS_UWP
                    file.Close();
#else
                    file.Dispose();
#endif
                }

                _assetCache.BufferCache[bufferIndex] = bufferData;
            }
        }
예제 #10
0
        /// <summary>
        /// Create a GLTFExporter that exports out a transform
        /// </summary>
        /// <param name="rootTransforms">Root transform of object to export</param>
        public GLTFSceneExporter(Transform[] rootTransforms, RetrieveTexturePathDelegate retrieveTexturePathDelegate)
        {
            _retrieveTexturePathDelegate = retrieveTexturePathDelegate;

            var metalGlossChannelSwapShader = Resources.Load("MetalGlossChannelSwap", typeof(UnityEngine.Shader)) as UnityEngine.Shader;

            _metalGlossChannelSwapMaterial = new UnityEngine.Material(metalGlossChannelSwapShader);

            var normalChannelShader = Resources.Load("NormalChannel", typeof(UnityEngine.Shader)) as UnityEngine.Shader;

            _normalChannelMaterial = new UnityEngine.Material(normalChannelShader);

            _rootTransforms = rootTransforms;
            _root           = new GLTFRoot {
                Accessors = new List <Accessor>(),
                Asset     = new Asset {
                    Version = "2.0"
                },
                Buffers     = new List <GLTF.Schema.Buffer>(),
                BufferViews = new List <BufferView>(),
                Images      = new List <Image>(),
                Materials   = new List <GLTF.Schema.Material>(),
                Meshes      = new List <GLTF.Schema.Mesh>(),
                Nodes       = new List <Node>(),
                Samplers    = new List <Sampler>(),
                Scenes      = new List <Scene>(),
                Textures    = new List <GLTF.Schema.Texture>(),
            };

            _imageInfos = new List <ImageInfo> ();
            _materials  = new List <UnityEngine.Material> ();
            _textures   = new List <UnityEngine.Texture> ();

            _buffer   = new GLTF.Schema.Buffer();
            _bufferId = new BufferId {
                Id   = _root.Buffers.Count,
                Root = _root
            };
            _root.Buffers.Add(_buffer);
        }
 private IEnumerator LoadBuffers()
 {
     if (_root.Buffers != null)
     {
         // todo add fuzzing to verify that buffers are before uri
         setProgress(IMPORT_STEP.BUFFER, 0, _root.Buffers.Count);
         for (int i = 0; i < _root.Buffers.Count; ++i)
         {
             GLTF.Schema.Buffer buffer = _root.Buffers[i];
             if (buffer.Uri != null)
             {
                 LoadBuffer(_gltfDirectoryPath, buffer, i);
             }
             else                     //null buffer uri indicates GLB buffer loading
             {
                 byte[] glbBuffer;
                 GLTFParser.ExtractBinaryChunk(_glTFData, i, out glbBuffer);
                 _assetCache.BufferCache[i] = glbBuffer;
             }
             setProgress(IMPORT_STEP.BUFFER, (i + 1), _root.Buffers.Count);
             yield return(null);
         }
     }
 }
예제 #12
0
        /// <summary>
        /// Creates a scene based off loaded JSON. Includes loading in binary and image data to construct the meshes required.
        /// </summary>
        /// <param name="sceneIndex">The index of scene in gltf file to load</param>
        /// <param name="isMultithreaded">Whether to use a thread to do loading</param>
        /// <returns></returns>
        protected IEnumerator ImportScene(int sceneIndex = -1, bool isMultithreaded = false)
        {
            Scene scene;

            if (sceneIndex >= 0 && sceneIndex < _root.Scenes.Count)
            {
                scene = _root.Scenes[sceneIndex];
            }
            else
            {
                scene = _root.GetDefaultScene();
            }

            if (scene == null)
            {
                throw new Exception("No default scene in gltf file.");
            }

            _assetCache = new AssetCache(
                _root.Images != null ? _root.Images.Count : 0,
                _root.Textures != null ? _root.Textures.Count : 0,
                _root.Materials != null ? _root.Materials.Count : 0,
                _root.Buffers != null ? _root.Buffers.Count : 0,
                _root.Meshes != null ? _root.Meshes.Count : 0
                );

            if (_lastLoadedScene == null)
            {
                if (_root.Buffers != null)
                {
                    // todo add fuzzing to verify that buffers are before uri
                    for (int i = 0; i < _root.Buffers.Count; ++i)
                    {
                        GLTF.Schema.Buffer buffer = _root.Buffers[i];
                        if (buffer.Uri != null)
                        {
                            yield return(LoadBuffer(_gltfDirectoryPath, buffer, i));
                        }
                        else                         //null buffer uri indicates GLB buffer loading
                        {
                            byte[] glbBuffer;
                            GLTFParser.ExtractBinaryChunk(_gltfData, i, out glbBuffer);
                            _assetCache.BufferCache[i] = glbBuffer;
                        }
                    }
                }

                if (_root.Images != null)
                {
                    for (int i = 0; i < _root.Images.Count; ++i)
                    {
                        Image image = _root.Images[i];
                        yield return(LoadImage(_gltfDirectoryPath, image, i));
                    }
                }
#if !WINDOWS_UWP
                // generate these in advance instead of as-needed
                if (isMultithreaded)
                {
                    yield return(_asyncAction.RunOnWorkerThread(() => BuildAttributesForMeshes()));
                }
#endif
            }

            var sceneObj = CreateScene(scene);

            if (_sceneParent != null)
            {
                sceneObj.transform.SetParent(_sceneParent, false);
            }

            _lastLoadedScene = sceneObj;
        }
예제 #13
0
        public static GLTFRoot Deserialize(TextReader textReader)
        {
            var jsonReader = new JsonTextReader(textReader);
            var root       = new GLTFRoot();

            if (jsonReader.Read() && jsonReader.TokenType != JsonToken.StartObject)
            {
                throw new Exception("gltf json must be an object");
            }

            while (jsonReader.Read() && jsonReader.TokenType == JsonToken.PropertyName)
            {
                var curProp = jsonReader.Value.ToString();

                switch (curProp)
                {
                case "extensionsUsed":
                    root.ExtensionsUsed = jsonReader.ReadStringList();
                    break;

                case "extensionsRequired":
                    root.ExtensionsRequired = jsonReader.ReadStringList();
                    break;

                case "accessors":
                    root.Accessors = jsonReader.ReadList(() => Accessor.Deserialize(root, jsonReader));
                    break;

                case "animations":
                    root.Animations = jsonReader.ReadList(() => Animation.Deserialize(root, jsonReader));
                    break;

                case "asset":
                    root.Asset = Asset.Deserialize(root, jsonReader);
                    break;

                case "buffers":
                    root.Buffers = jsonReader.ReadList(() => Buffer.Deserialize(root, jsonReader));
                    break;

                case "bufferViews":
                    root.BufferViews = jsonReader.ReadList(() => BufferView.Deserialize(root, jsonReader));
                    break;

                case "cameras":
                    root.Cameras = jsonReader.ReadList(() => Camera.Deserialize(root, jsonReader));
                    break;

                case "images":
                    root.Images = jsonReader.ReadList(() => Image.Deserialize(root, jsonReader));
                    break;

                case "materials":
                    root.Materials = jsonReader.ReadList(() => Material.Deserialize(root, jsonReader));
                    break;

                case "meshes":
                    root.Meshes = jsonReader.ReadList(() => Mesh.Deserialize(root, jsonReader));
                    break;

                case "nodes":
                    root.Nodes = jsonReader.ReadList(() => Node.Deserialize(root, jsonReader));
                    break;

                case "samplers":
                    root.Samplers = jsonReader.ReadList(() => Sampler.Deserialize(root, jsonReader));
                    break;

                case "scene":
                    root.Scene = SceneId.Deserialize(root, jsonReader);
                    break;

                case "scenes":
                    root.Scenes = jsonReader.ReadList(() => GLTF.Schema.Scene.Deserialize(root, jsonReader));
                    break;

                case "skins":
                    root.Skins = jsonReader.ReadList(() => Skin.Deserialize(root, jsonReader));
                    break;

                case "textures":
                    root.Textures = jsonReader.ReadList(() => Texture.Deserialize(root, jsonReader));
                    break;

                default:
                    root.DefaultPropertyDeserializer(root, jsonReader);
                    break;
                }
            }

            return(root);
        }
예제 #14
0
        /// <summary>
        /// Creates a scene based off loaded JSON. Includes loading in binary and image data to construct the meshes required.
        /// </summary>
        /// <param name="sceneIndex">The index of scene in gltf file to load</param>
        /// <param name="isMultithreaded">Whether to use a thread to do loading</param>
        /// <returns></returns>
        protected IEnumerator ImportScene(int sceneIndex = -1, bool isMultithreaded = false)
        {
            GLTF.Schema.Scene scene;
            if (sceneIndex >= 0 && sceneIndex < _root.Scenes.Count)
            {
                scene = _root.Scenes[sceneIndex];
            }
            else
            {
                scene = _root.GetDefaultScene();
            }

            if (scene == null)
            {
                throw new Exception("No default scene in gltf file.");
            }

            _assetCache = new AssetCache(
                _root.Images != null ? _root.Images.Count : 0,
                _root.Textures != null ? _root.Textures.Count : 0,
                _root.Materials != null ? _root.Materials.Count : 0,
                _root.Buffers != null ? _root.Buffers.Count : 0,
                _root.Meshes != null ? _root.Meshes.Count : 0
                );

            if (_lastLoadedScene == null)
            {
                if (_root.Buffers != null)
                {
                    // todo add fuzzing to verify that buffers are before uri
                    for (int i = 0; i < _root.Buffers.Count; ++i)
                    {
                        GLTF.Schema.Buffer buffer = _root.Buffers[i];
                        if (buffer.Uri != null)
                        {
                            yield return(LoadBuffer(_gltfDirectoryPath, buffer, i));
                        }
                        else                         //null buffer uri indicates GLB buffer loading
                        {
                            byte[] glbBuffer;
                            GLTFParser.ExtractBinaryChunk(_gltfData, i, out glbBuffer);
                            _assetCache.BufferCache[i] = glbBuffer;
                        }
                    }
                }

                if (_root.Images != null)
                {
                    for (int i = 0; i < _root.Images.Count; ++i)
                    {
                        GLTF.Schema.Image image = _root.Images[i];
                        yield return(LoadImage(_gltfDirectoryPath, image, i));
                    }
                }
#if !WINDOWS_UWP
                // generate these in advance instead of as-needed
                if (isMultithreaded)
                {
                    yield return(_asyncAction.RunOnWorkerThread(() => BuildAttributesForMeshes()));
                }
#endif
            }

            var sceneObj = CreateScene(scene);

            if (_sceneParent != null)
            {
                sceneObj.transform.SetParent(_sceneParent, false);
            }

            // Experiment with fitting the scene into a prescribed size by accumulating
            // all of the scenes nodes bounding boxes and then scaling the root node
            // (I think this would be better as a mode to scale vertices but not for now..)
            var allRenderersInScene = sceneObj.GetComponentsInChildren <Renderer>(false);

            Bounds?box = null;

            foreach (var renderer in allRenderersInScene)
            {
                //CreateBox(sceneObj.transform, renderer.bounds);

                if (!box.HasValue)
                {
                    box = new Bounds(renderer.bounds.center, renderer.bounds.size);
                }
                else
                {
                    var val = box.Value;
                    val.Encapsulate(renderer.bounds);
                    box = val;
                }
            }

            //CreateBox(sceneObj.transform, box);

            // Now, for each individual mesh we can move the pivot to the bottom/centre
            // w.r.t the vertices. This way we can easily place models on a flat surface
            var allMeshesInScene = sceneObj.GetComponentsInChildren <MeshFilter>(false);
            foreach (var renderer in allMeshesInScene)
            {
                var bbox = renderer.mesh.bounds;

                // Calculate the distances we need to shift all of the vertices in
                // each direction to get them centred in x and z and have them sitting
                // at zero in the y-axis
                float adjustY = bbox.center.y;
                float adjustx = bbox.center.x;
                float adjustZ = bbox.center.z;

                //var verts = renderer.mesh.vertices;
                //for (int i = 0; i < verts.Length; i++)
                //{
                //    verts[i].x = verts[i].x - adjustx;
                //    verts[i].y = verts[i].y - adjustY;
                //    verts[i].z = verts[i].z - adjustZ;
                //}

                //renderer.mesh.vertices = verts;
            }


            Vector3 targetSize      = Vector3.one / 4.0f;
            Vector3 sceneBoundsSize = box.Value.max - box.Value.min;

            float ratioX = targetSize.x / sceneBoundsSize.x;
            float ratioY = targetSize.y / sceneBoundsSize.y;
            float ratioZ = targetSize.z / sceneBoundsSize.z;

            float biggest = Math.Min(ratioZ, Math.Min(ratioX, ratioY));

            //sceneObj.transform.localScale = sceneObj.transform.localScale *
            //    (componentMax(targetSize) / componentMax(sceneBoundsSize));

            //float f = componentMax(div(targetSize, sceneBoundsSize));

            sceneObj.transform.localScale = sceneObj.transform.localScale * biggest;

            _lastLoadedScene = sceneObj;
        }