Exemple #1
0
        public static async Task <SceneCollection> ImportAsync(
            string filePath,
            ColladaImportOptions options,
            Progress <float> progress,
            CancellationToken cancel)
        {
            if (!File.Exists(filePath))
            {
                return(null);
            }

            ImportOptions = options;
            SceneCollection scenes = new SceneCollection();

            var schemeReader = new XMLSchemaDefinition <COLLADA>();
            var root         = await schemeReader.ImportAsync(filePath, (ulong)options.IgnoreFlags, progress, cancel);

            if (root != null)
            {
                Matrix4 baseTransform = options.InitialTransform.Matrix;
                var     asset         = root.AssetElement;
                if (asset != null)
                {
                    var unit  = asset.UnitElement;
                    var coord = asset.UpAxisElement;

                    if (unit != null)
                    {
                        WriteLine($"Units: {unit.Name} (to meters: {unit.Meter.ToString()})");
                        baseTransform = baseTransform * Matrix4.CreateScale(unit.Meter);
                    }
                    if (coord != null)
                    {
                        WriteLine("Up axis: " + coord.StringContent.Value.ToString());
                        switch (coord.StringContent.Value)
                        {
                        case Asset.EUpAxis.X_UP:
                            baseTransform = Matrix4.XupToYup * baseTransform;
                            break;

                        case Asset.EUpAxis.Y_UP:
                            break;

                        case Asset.EUpAxis.Z_UP:
                            baseTransform = Matrix4.ZupToYup * baseTransform;
                            break;
                        }
                    }
                }

                COLLADA.Scene scene = root.GetChild <COLLADA.Scene>();
                if (scene != null)
                {
                    var visualScenes = scene.GetChildren <COLLADA.Scene.InstanceVisualScene>();
                    foreach (var visualSceneRef in visualScenes)
                    {
                        var visualScene = visualSceneRef.GetUrlInstance();
                        if (visualScene != null)
                        {
                            Scene colladaScene = new Scene();

                            //Collect information for objects and root bones
                            List <Bone>       rootBones = new List <Bone>();
                            List <ObjectInfo> objects   = new List <ObjectInfo>();
                            List <Camera>     cameras   = new List <Camera>();
                            List <Light>      lights    = new List <Light>();

                            var nodes = visualScene.NodeElements;
                            foreach (var node in nodes)
                            {
                                Bone b = EnumNode(null, node, nodes, objects, baseTransform, Matrix4.Identity, lights, cameras, options.IgnoreFlags);
                                if (b != null)
                                {
                                    rootBones.Add(b);
                                }
                            }

                            colladaScene.Model = new Model()
                            {
                                Name = Path.GetFileNameWithoutExtension(filePath)
                            };

                            //Create meshes after all bones have been created
                            bool hasBones = rootBones.Count != 0;
                            if (hasBones)
                            {
                                colladaScene.Model.Skeleton = new Skeleton(rootBones.ToArray());
                            }

                            foreach (ObjectInfo obj in objects)
                            {
                                if (obj.UsesController && !hasBones)
                                {
                                    WriteLine($"Object {obj._node.Name} uses bones but the model has none. Skipping this object.");
                                    continue;
                                }
                                obj.Initialize(colladaScene.Model, visualScene, options.GenerateBinormals, options.GenerateTangents);
                            }

                            scenes.Scenes.Add(colladaScene);

                            //if (!options.IgnoreFlags.HasFlag(EIgnoreFlags.Animations))
                            //{
                            //    SkeletalAnimation anim = null;
                            //    float animationLength = 0.0f;
                            //    foreach (LibraryAnimations lib in root.GetLibraries<LibraryAnimations>())
                            //        foreach (LibraryAnimations.Animation animElem in lib.AnimationElements)
                            //        {
                            //            if (anim == null)
                            //            {
                            //                data.PropertyAnimations = new List<BasePropAnim>();
                            //                anim = new SkeletalAnimation()
                            //                {
                            //                    Name = Path.GetFileNameWithoutExtension(filePath),
                            //                    Looped = true,
                            //                };
                            //            }
                            //            ParseAnimation(animElem, anim, visualScene, data.PropertyAnimations, ref animationLength);
                            //        }

                            //    if (anim != null && animationLength > 0.0f)
                            //    {
                            //        anim.SetLength(animationLength, false);
                            //        PrintLine("Model animation imported: " + animationLength.ToString() + " seconds / " + Math.Ceiling(animationLength * 60.0f).ToString() + " frames long at 60fps.");
                            //        data.Models[0].Animation = anim;
                            //    }
                            //}
                        }
                    }
                }
            }

            ImportOptions = null;
            return(scenes);
        }
Exemple #2
0
 public static Task <SceneCollection> ImportAsync(
     string filePath,
     ColladaImportOptions options)
 => ImportAsync(filePath, options, null, CancellationToken.None);