Exemplo n.º 1
0
        public static XDocument CreateOutputDocument(string projectPath, string projectName, string relativeSourceFilePath)
        {
            // create sourceFilePath
            var sourceFilePath = projectPath + relativeSourceFilePath;

            // if source file does not exist throw exception
            if (!File.Exists(sourceFilePath))
            {
                Helpers.ThrowException <Exception>(SOURCE_EXCEPTION + sourceFilePath);
            }

            // load source doc
            var sourceDoc = XDocument.Load(sourceFilePath);

            // get default namespace for doc creation and filtering
            var defaultNameSpace = sourceDoc.Root.GetDefaultNamespace();

            // get res dict string
            var resDictString = sourceDoc.Root.Name.LocalName;

            var outputDoc = XDocument.Parse("<" + resDictString + " xmlns=\"" + defaultNameSpace + "\"/>");

            // create documents
            var documents = new Dictionary <string, Data>();

            // add elements
            ResourceMerger.PrepareDocuments(ref documents, projectPath, projectName, relativeSourceFilePath);

            // add elements (ordered by dependency count)
            foreach (var item in documents.OrderByDescending(item => item.Value.DependencyCount))
            {
                // add attributes
                foreach (var attribute in item.Value.Document.Root.Attributes())
                {
                    outputDoc.Root.SetAttributeValue(attribute.Name, attribute.Value);
                }

                // add elements
                outputDoc.Root.Add(item.Value.Document.Root.Elements().Where(e => !e.Name.LocalName.StartsWith(resDictString)));
            }

            return(outputDoc);
        }
Exemplo n.º 2
0
        /// <summary>
        /// save all resources into one big resource dictionary respecting the dependencies to increase performance
        /// </summary>
        /// <param name="projectPath">project path (C:/..)</param>
        /// <param name="relativeSourceFilePath">relative source file path (/LookAndFeel.xaml)</param>
        /// <param name="relativeOutputFilePath">relative output file path (/xGeneric/Generic.xaml)</param>
        /// <param name="projectName">project name</param>
        /// <param name="resDictString">resource dictionary string (node name)</param>
        public static void MergeResources(string projectPath, string projectName = null, string relativeSourceFilePath = "/LookAndFeel.xaml", string relativeOutputFilePath = "/FullLookAndFeel.xaml")
        {
            if (!Directory.Exists(projectPath))
            {
                Helpers.ThrowException <Exception>(PROJECT_PATH_EXCEPTION);
            }

            projectName = string.IsNullOrEmpty(projectName) ? Path.GetFileName(Path.GetDirectoryName(projectPath)) : projectName;

            if (!relativeSourceFilePath.EndsWith(".xaml", StringComparison.InvariantCultureIgnoreCase))
            {
                Helpers.ThrowException <Exception>(SOURCE_TYPE_EXCEPTION);
            }

            if (!relativeOutputFilePath.EndsWith(".xaml", StringComparison.InvariantCultureIgnoreCase))
            {
                Helpers.ThrowException <Exception>(OUTPUT_TYPE_EXCEPTION);
            }

            var documents          = new Dictionary <string, Data>();
            var existingNamespaces = new List <Namespace>();

            ResourceMerger.PrepareDocuments(documents, projectPath, projectName, relativeSourceFilePath, existingNamespaces);

            var existingKeys = new HashSet <string>();

            var sourceDoc        = LoadDocument(projectPath, relativeSourceFilePath);
            var resDictString    = sourceDoc.Root.Name.LocalName;
            var defaultNameSpace = sourceDoc.Root.GetDefaultNamespace();
            var outputDoc        = XDocument.Parse("<" + resDictString + " xmlns=\"" + defaultNameSpace + "\"/>");

            foreach (var item in documents.OrderByDescending(item => item.Value.DependencyCount))
            {
                // add attributes
                foreach (var attribute in item.Value.Document.Root.Attributes())
                {
                    outputDoc.Root.SetAttributeValue(attribute.Name, attribute.Value);
                }

                var elements    = item.Value.Document.Root.Elements().Where(e => !e.Name.LocalName.StartsWith(resDictString)).ToList();
                var elementKeys = elements.Select(GetKey);

                // TODO: not sure about this part. our xamls contained duplicate keys such as "BooleanToVisibilityConverter".
                //       obviously we need only one of them. but if two keys actually reference completely different things, this might be a bad idea
                //       better warn the user and let him fix it?
                outputDoc.Root.Add(elements.Where(e => !existingKeys.Contains(GetKey(e))));

                existingKeys.UnionWith(elementKeys);
                existingKeys.ExceptWith(new string[] { null });
            }

            using (var ms = new MemoryStream())
            {
                outputDoc.Save(ms);

                // TODO: I don't think we need this. If we include this into our build process, we don't wanna waste time
                if (OutputEqualsExistingFileContent(Path.Combine(projectPath, relativeOutputFilePath), ms.ToArray()))
                {
                    return;
                }
            }

            outputDoc.Save(projectPath + relativeOutputFilePath);
        }
Exemplo n.º 3
0
        /// <summary>
        /// save all resources into one big resource dictionary respecting the dependencies to increase performance
        /// </summary>
        /// <param name="projectPath">project path (C:/..)</param>
        /// <param name="relativeSourceFilePath">relative source file path (/LookAndFeel.xaml)</param>
        /// <param name="relativeOutputFilePath">relative output file path (/xGeneric/Generic.xaml)</param>
        /// <param name="projectName">project name</param>
        /// <param name="resDictString">resource dictionary string (node name)</param>
        public static void MergeResources(string projectPath, string projectName = null, string relativeSourceFilePath = "/LookAndFeel.xaml", string relativeOutputFilePath = "/FullLookAndFeel.xaml")
        {
            // if project path does not exist throw exception
            if (!Directory.Exists(projectPath))
            {
                Helpers.ThrowException <Exception>(PROJECT_PATH_EXCEPTION);
            }

            // Get default values for optional parameters
            projectName = string.IsNullOrEmpty(projectName) ? Path.GetFileName(Path.GetDirectoryName(projectPath)) : projectName;

            // if relativeSourceFilePath is not of type .xaml throw exception
            if (!relativeSourceFilePath.EndsWith(".xaml", StringComparison.InvariantCultureIgnoreCase))
            {
                Helpers.ThrowException <Exception>(SOURCE_TYPE_EXCEPTION);
            }

            // if relativeOutputFilePath is not of type .xaml throw exception
            if (!relativeOutputFilePath.EndsWith(".xaml", StringComparison.InvariantCultureIgnoreCase))
            {
                Helpers.ThrowException <Exception>(OUTPUT_TYPE_EXCEPTION);
            }

            // create sourceFilePath
            var sourceFilePath = projectPath + relativeSourceFilePath;

            // if source file does not exist throw exception
            if (!File.Exists(sourceFilePath))
            {
                Helpers.ThrowException <Exception>(SOURCE_EXCEPTION + sourceFilePath);
            }

            // load source doc
            var sourceDoc = XDocument.Load(sourceFilePath);

            // get default namespace for doc creation and filtering
            var defaultNameSpace = sourceDoc.Root.GetDefaultNamespace();

            // get res dict string
            var resDictString = sourceDoc.Root.Name.LocalName;

            // create output doc
            var outputDoc = XDocument.Parse("<" + resDictString + " xmlns=\"" + defaultNameSpace + "\"/>");

            // create documents
            var documents = new Dictionary <string, Data>();

            // add elements
            ResourceMerger.PrepareDocuments(ref documents, projectPath, projectName, relativeSourceFilePath);

            // add elements (ordered by dependency count)
            foreach (var item in documents.OrderByDescending(item => item.Value.DependencyCount))
            {
                // add attributes
                foreach (var attribute in item.Value.Document.Root.Attributes())
                {
                    outputDoc.Root.SetAttributeValue(attribute.Name, attribute.Value);
                }

                // add elements
                outputDoc.Root.Add(item.Value.Document.Root.Elements().Where(e => !e.Name.LocalName.StartsWith(resDictString)));
            }

            using (var ms = new MemoryStream())
            {
                outputDoc.Save(ms);

                if (OutputEqualsExistingFileContent(Path.Combine(projectPath, relativeOutputFilePath), ms.ToArray()))
                {
                    return;
                }
            }

            // save file
            outputDoc.Save(projectPath + relativeOutputFilePath);
        }
Exemplo n.º 4
0
        /// <summary>
        /// save all resources into one big resource dictionary respecting the dependencies to increase performance
        /// </summary>
        /// <param name="projectPath">project path (C:/..)</param>
        /// <param name="relativeSourceFilePath">relative source file path (/LookAndFeel.xaml)</param>
        /// <param name="relativeOutputFilePath">relative output file path (/xGeneric/Generic.xaml)</param>
        /// <param name="projectName">project name</param>
        /// <param name="resDictString">resource dictionary string (node name)</param>
        public static void MergeResources(string projectPath, string projectName = null, string relativeSourceFilePath = "/LookAndFeel.xaml", string relativeOutputFilePath = "/FullLookAndFeel.xaml")
        {
            // if project path does not exist throw exception
            if (!Directory.Exists(projectPath))
            {
                throw new DirectoryNotFoundException($"Project path `{projectPath}` does not exist.");
            }

            // Get default values for optional parameters
            projectName = string.IsNullOrEmpty(projectName) ? Path.GetFileName(Path.GetDirectoryName(projectPath)) : projectName;

            // if relativeSourceFilePath is not of type .xaml throw exception
            if (!relativeSourceFilePath.EndsWith(".xaml", StringComparison.InvariantCultureIgnoreCase))
            {
                throw new InvalidOperationException($"The relative source file `{relativeSourceFilePath}` should have a .xaml extension.");
            }

            // if relativeOutputFilePath is not of type .xaml throw exception
            if (!relativeOutputFilePath.EndsWith(".xaml", StringComparison.InvariantCultureIgnoreCase))
            {
                throw new InvalidOperationException($"The relative output file `{relativeOutputFilePath}` should have a .xaml extension.");
            }

            // create sourceFilePath
            var sourceFilePath = projectPath + relativeSourceFilePath;

            // if source file does not exist throw exception
            if (!File.Exists(sourceFilePath))
            {
                throw new FileNotFoundException($"The source file `{sourceFilePath}` was not found.");
            }

            // load source doc
            var sourceDoc = XDocument.Load(sourceFilePath);

            // get default namespace for doc creation and filtering
            var defaultNameSpace = sourceDoc.Root.GetDefaultNamespace();

            // get res dict string
            var resDictString = sourceDoc.Root.Name.LocalName;

            // create output doc
            var outputDoc = XDocument.Parse("<" + resDictString + " xmlns=\"" + defaultNameSpace + "\"/>");

            // create documents
            var documents = new Dictionary <string, Data>();

            // create dictionary for references that cannot be resolved locally.
            var unresolvedRefs = new HashSet <string>();

            // add elements
            ResourceMerger.PrepareDocuments(ref documents, unresolvedRefs, projectPath, projectName, relativeSourceFilePath);

            // add referenced elements
            if (unresolvedRefs.Any())
            {
                var xnsp = outputDoc.Root.GetDefaultNamespace();

                var mergedDicts = unresolvedRefs
                                  .Select(x => new XElement(xnsp + resDictString, new XAttribute("Source", x)))
                                  .ToArray();

                var elm = new XElement(xnsp + resDictString + ".MergedDictionaries", mergedDicts);
                outputDoc.Root.Add(elm);
            }

            // add elements (ordered by dependency count)
            foreach (var item in documents.OrderByDescending(item => item.Value.DependencyCount))
            {
                // add attributes
                foreach (var attribute in item.Value.Document.Root.Attributes())
                {
                    outputDoc.Root.SetAttributeValue(attribute.Name, attribute.Value);
                }

                // add elements
                outputDoc.Root.Add(item.Value.Document.Root.Elements().Where(e => !e.Name.LocalName.StartsWith(resDictString)));
            }

            using (var ms = new MemoryStream())
            {
                outputDoc.Save(ms);

                if (OutputEqualsExistingFileContent(Path.Combine(projectPath, relativeOutputFilePath), ms.ToArray()))
                {
                    return;
                }
            }

            // save file
            outputDoc.Save(projectPath + relativeOutputFilePath);
        }