예제 #1
0
        public void TestReduction()
        {
            var materialAsset = AssetSerializer.Load <MaterialAsset>("materials/testReduction.pdxmat");

            var materialReducer = new MaterialTreeReducer(materialAsset.Material);

            materialReducer.ReduceTrees();

            var reducedTrees = materialReducer.ReducedTrees;

            Assert.IsTrue(reducedTrees["diffuse"] is MaterialFloat4Node);
        }
예제 #2
0
        public void TestSave()
        {
            var materialAsset = AssetSerializer.Load <MaterialAsset>("materials/testMaterial.pdxmat");

            var materialReducer = new MaterialTreeReducer(materialAsset.Material);

            materialReducer.ReduceTrees();

            var reducedTrees = materialReducer.ReducedTrees;

            foreach (var reducedTree in reducedTrees)
            {
                materialAsset.Material.AddNode(reducedTree.Key + "_reduced", reducedTree.Value);
            }

            var model = new MaterialDescription();

            model.SetParameter(MaterialParameters.UseTransparent, true);
            model.SetParameter(MaterialParameters.ShadingModel, MaterialShadingModel.Phong);
            model.SetParameter(MaterialParameters.DiffuseModel, MaterialDiffuseModel.Lambert);
            model.SetParameter(MaterialParameters.SpecularModel, MaterialSpecularModel.BlinnPhong);
            model.SetParameter(MaterialKeys.DiffuseColorValue, new Color4(1.0f, 1.0f, 0.5f, 0.5f));
            model.SetParameter(MaterialKeys.SpecularColorValue, new Color4(0.4f, 0.1f, 1.0f, 1.0f));
            model.SetParameter(MaterialKeys.SpecularIntensity, 1.1f);
            model.SetParameter(MaterialKeys.SpecularPower, 10.1f);

            var defaultModel = materialAsset.Material;

            foreach (var treeName in defaultModel.ColorNodes)
            {
                model.ColorNodes.Add(treeName.Key, treeName.Value + "_reduced");
            }

            var matAsset2 = new MaterialAsset {
                Material = model
            };

            AssetSerializer.Save("testMaterial2.pdxmat", matAsset2);

            var savedAsset     = AssetSerializer.Load <MaterialAsset>("testMaterial2.pdxmat");
            var loadedMaterial = savedAsset.Material;

            Assert.AreEqual(true, loadedMaterial.GetParameter(MaterialParameters.UseTransparent));
            Assert.AreEqual(MaterialShadingModel.Phong, loadedMaterial.GetParameter(MaterialParameters.ShadingModel));
            Assert.AreEqual(MaterialDiffuseModel.Lambert, loadedMaterial.GetParameter(MaterialParameters.DiffuseModel));
            Assert.AreEqual(MaterialSpecularModel.BlinnPhong, loadedMaterial.GetParameter(MaterialParameters.SpecularModel));
            Assert.AreEqual(new Color4(1.0f, 1.0f, 0.5f, 0.5f), loadedMaterial.GetParameter(MaterialKeys.DiffuseColorValue));
            Assert.AreEqual(new Color4(0.4f, 0.1f, 1.0f, 1.0f), loadedMaterial.GetParameter(MaterialKeys.SpecularColorValue));
            Assert.AreEqual(1.1f, loadedMaterial.GetParameter(MaterialKeys.SpecularIntensity));
            Assert.AreEqual(10.1f, loadedMaterial.GetParameter(MaterialKeys.SpecularPower));
        }
예제 #3
0
        /// <summary>
        /// Create the structures to perform the reductions.
        /// </summary>
        public void PrepareForFlattening(UDirectory baseDir = null)
        {
            var reducer = new MaterialTreeReducer(Material);

            reducer.ReduceTrees();
            var reducedTrees   = reducer.ReducedTrees;
            var textureVisitor = new MaterialTextureVisitor(Material);

            foreach (var materialReference in reducedTrees)
            {
                Material.Nodes[materialReference.Key] = materialReference.Value;
                textureVisitor.AssignDefaultTextureKeys(materialReference.Value);
            }

            commandList.Clear();
            textureVisitor.ResetTextureIndices();

            var basePath = (baseDir == null || baseDir.GetDirectory() == "" ? "" : baseDir.ToString() + "/") + "__reduced_textures__";

            foreach (var materialReferenceKey in Material.Nodes)
            {
                if (materialReferenceKey.Value == null)
                {
                    continue;
                }

                var materialReferenceName = materialReferenceKey.Key;
                var materialNode          = materialReferenceKey.Value;
                textureVisitor.AssignDefaultTextureKeys(materialNode);
                var nodesToReduce = reducer.GetReducibleSubTrees(materialNode);

                for (var i = 0; i < nodesToReduce.Count; ++i)
                {
                    var nodeToReduce    = nodesToReduce[i];
                    var finalTextureUrl = new UFile(basePath, materialReferenceName + "_Texture" + (nodesToReduce.Count > 1 ? i.ToString() : ""), null);
                    var infos           = new MaterialReductionInfo {
                        ToExecute = false, TextureUrl = finalTextureUrl
                    };
                    var canBeReduced = textureVisitor.HasUniqueTexcoord(nodeToReduce, out infos.TexcoordIndex);
                    infos.OldNode = nodeToReduce;

                    if (!canBeReduced)
                    {
                        continue; // throw new Exception("Unsolvable tree");
                    }
                    commandList.Add(infos);
                }
            }
        }
예제 #4
0
            protected override Task <ResultStatus> DoCommandOverride(ICommandContext commandContext)
            {
                var material = asset.Material.Clone();

                // Replace all empty Texture nodes by black color texture nodes (allow a display of the element even if material is incomplete)
                var emptyTextureNodeKeys = material.Nodes.Where(m => m.Value is MaterialTextureNode && !IsTextureReferenceValid((MaterialTextureNode)m.Value)).Select(m => m.Key).ToList();

                foreach (var emptyTextureNodeKey in emptyTextureNodeKeys)
                {
                    commandContext.Logger.Warning("Texture node '{0}' of material '{1}' is not pointing to a valid texture reference. " +
                                                  "This node will be replaced by black color Node.", emptyTextureNodeKey, assetItem.Location);
                    material.Nodes[emptyTextureNodeKey] = new MaterialColorNode(new Color4(0));
                }

                // Reduce trees on CPU
                var materialReducer = new MaterialTreeReducer(material);

                materialReducer.ReduceTrees();

                foreach (var reducedTree in materialReducer.ReducedTrees)
                {
                    material.Nodes[reducedTree.Key] = reducedTree.Value;
                }

                // Reduce on GPU
                // TODO: Adapt GPU reduction so that it is compatible Android color/alpha separation
                // TODO: Use the build engine processed output textures instead of the imported one (not existing any more)
                // TODO: Set the reduced texture output format
                // TODO: The graphics device cannot be shared with the Previewer
                //var graphicsDevice = (GraphicsDevice)context.Attributes.GetOrAdd(CompilerContext.GraphicsDeviceKey, key => GraphicsDevice.New(DeviceCreationFlags.None, GraphicsProfile.Level_11_0));
                //using (var materialTextureLayerFlattener = new MaterialTextureLayerFlattener(material, graphicsDevice))
                //{
                //    materialTextureLayerFlattener.PrepareForFlattening(new UDirectory(assetUrl.Directory));
                //    if (materialTextureLayerFlattener.HasCommands)
                //    {
                //        var compiler = EffectCompileCommand.GetOrCreateEffectCompiler(context);
                //        materialTextureLayerFlattener.Run(compiler);
                //        // store Material with modified textures
                //        material = materialTextureLayerFlattener.Material;
                //    }
                //}

                // Separate the textures into color/alpha components on Android to be able to use native ETC1 compression
                if (context.Platform == PlatformType.Android)
                {
                    var alphaComponentSplitter = new TextureAlphaComponentSplitter(assetItem.Package.Session);
                    material = alphaComponentSplitter.Run(material, new UDirectory(assetUrl.GetDirectory())); // store Material with alpha substituted textures
                }

                // Create the parameters
                var materialParameterCreator = new MaterialParametersCreator(material, assetUrl);

                if (materialParameterCreator.CreateParameterCollectionData(commandContext.Logger))
                {
                    return(Task.FromResult(ResultStatus.Failed));
                }

                var materialData = new MaterialData {
                    Parameters = materialParameterCreator.Parameters
                };

                var assetManager = new AssetManager();

                assetManager.Save(assetUrl, materialData);

                return(Task.FromResult(ResultStatus.Successful));
            }