private bool Converter(string srcPath, string dstPath) { var cookingRules = AssetCooker.CookingRulesMap[srcPath]; var compression = cookingRules.ModelCompression; Model3D model; var options = new FbxImportOptions { Path = srcPath, Target = AssetCooker.Target, CookingRulesMap = AssetCooker.CookingRulesMap }; using (var fbxImporter = new FbxModelImporter(options)) { model = fbxImporter.LoadModel(); } AssetAttributes assetAttributes; switch (compression) { case ModelCompression.None: assetAttributes = AssetAttributes.None; break; case ModelCompression.Deflate: assetAttributes = AssetAttributes.ZippedDeflate; break; case ModelCompression.LZMA: assetAttributes = AssetAttributes.ZippedLZMA; break; default: throw new ArgumentOutOfRangeException($"Unknown compression: {compression}"); } var animationPathPrefix = AssetCooker.GetModelAnimationPathPrefix(dstPath); AssetCooker.DeleteModelExternalAnimations(animationPathPrefix); AssetCooker.ExportModelAnimations(model, animationPathPrefix, assetAttributes, cookingRules.SHA1); model.RemoveAnimatorsForExternalAnimations(); InternalPersistence.Instance.WriteObjectToBundle(AssetCooker.AssetBundle, dstPath, model, Persistence.Format.Binary, t3dExtension, File.GetLastWriteTime(srcPath), assetAttributes, cookingRules.SHA1); return(true); }
private void CheckFbx(string path) { var target = Orange.The.UI.GetActiveTarget(); using (var cacheBundle = OpenCacheBundle(AssetBundleFlags.Writable)) { Model3DAttachment attachment = null; Model3D model = null; var fbxPath = Path.ChangeExtension(path, "fbx"); var fbxExists = base.FileExists(fbxPath); var fbxCached = cacheBundle.FileExists(path); var fbxUpToDate = fbxCached == fbxExists && (!fbxExists || cacheBundle.GetFileLastWriteTime(path) >= base.GetFileLastWriteTime(fbxPath)); var attachmentPath = Path.ChangeExtension(path, Model3DAttachment.FileExtension); var attachmentExists = base.FileExists(attachmentPath); var attachmentCached = cacheBundle.FileExists(attachmentPath); var attachmentUpToDate = attachmentCached == attachmentExists && (!attachmentExists || cacheBundle.GetFileLastWriteTime(attachmentPath) >= base.GetFileLastWriteTime(attachmentPath)); var fbxImportOptions = new FbxImportOptions { Path = fbxPath, Target = target, ApplyAttachment = false }; var attachmentMetaPath = Path.ChangeExtension(path, Model3DAttachmentMeta.FileExtension); var attachmentMetaCached = cacheBundle.FileExists(attachmentMetaPath); var attachmentMetaUpToDate = attachmentMetaCached && cacheBundle.GetFileLastWriteTime(attachmentMetaPath) >= base.GetFileLastWriteTime(fbxPath); if (!attachmentMetaUpToDate && fbxExists) { using (var fbxImporter = new FbxModelImporter(fbxImportOptions)) { model = fbxImporter.LoadModel(); var meta = new Model3DAttachmentMeta(); foreach (var animation in model.Animations) { meta.SourceAnimationIds.Add(animation.Id); } foreach (var mesh in model.Descendants.OfType <Mesh3D>()) { meta.MeshIds.Add(mesh.Id); foreach (var submesh3D in mesh.Submeshes) { if (meta.SourceMaterials.All(m => m.Id != submesh3D.Material.Id)) { meta.SourceMaterials.Add(submesh3D.Material); } } } TangerinePersistence.Instance.WriteObjectToBundle( cacheBundle, attachmentMetaPath, meta, Persistence.Format.Binary, Model3DAttachmentMeta.FileExtension, base.GetFileLastWriteTime(fbxPath), AssetAttributes.None, new byte[0]); } } if (fbxUpToDate && attachmentUpToDate) { return; } var animationPathPrefix = Orange.Toolbox.ToUnixSlashes(Path.GetDirectoryName(path) + "/" + Path.GetFileNameWithoutExtension(path) + "@"); foreach (var assetPath in cacheBundle.EnumerateFiles().ToList()) { if (assetPath.EndsWith(".ant") && assetPath.StartsWith(animationPathPrefix)) { cacheBundle.DeleteFile(assetPath); } } if (fbxExists) { if (model == null) { using (var fbxImporter = new FbxModelImporter(fbxImportOptions)) { model = fbxImporter.LoadModel(); } } if (attachmentExists) { attachment = Model3DAttachmentParser.GetModel3DAttachment(fbxPath); if (attachment.Animations != null) { foreach (var animation in attachment.Animations) { if (animation.SourceAnimationId == null) { var ac = model.Components.Get <AnimationComponent>(); animation.SourceAnimationId = ac != null && ac.Animations.Count > 0 ? ac.Animations[0].Id : null; } } } attachment.Apply(model); } foreach (var animation in model.Animations) { if (animation.IsLegacy) { continue; } var animationPathWithoutExt = animationPathPrefix + animation.Id; animationPathWithoutExt = Animation.FixAntPath(animationPathWithoutExt); var animationPath = animationPathWithoutExt + ".ant"; animation.ContentsPath = animationPathWithoutExt; InternalPersistence.Instance.WriteObjectToBundle(cacheBundle, animationPath, animation.GetData(), Persistence.Format.Binary, ".ant", base.GetFileLastWriteTime(fbxPath), AssetAttributes.None, new byte[0]); var animators = new List <IAnimator>(); animation.FindAnimators(animators); foreach (var animator in animators) { animator.Owner.Animators.Remove(animator); } } TangerinePersistence.Instance.WriteObjectToBundle(cacheBundle, path, model, Persistence.Format.Binary, ".t3d", base.GetFileLastWriteTime(fbxPath), AssetAttributes.None, new byte[0]); } else if (fbxCached) { cacheBundle.DeleteFile(path); cacheBundle.DeleteFile(attachmentMetaPath); } if (attachmentExists) { TangerinePersistence.Instance.WriteObjectToBundle( cacheBundle, attachmentPath, Model3DAttachmentParser.ConvertToModelAttachmentFormat(attachment), Persistence.Format.Binary, ".txt", base.GetFileLastWriteTime(attachmentPath), AssetAttributes.None, new byte[0]); } else if (attachmentCached) { cacheBundle.DeleteFile(attachmentPath); } } }