Ejemplo n.º 1
0
        /// <summary>
        /// Parse a complex font property value that contains multiple css properties into specific css properties.
        /// </summary>
        /// <param name="propValue">the value of the property to parse to specific values</param>
        /// <param name="properties">the properties collection to add the specific properties to</param>
        private void ParseFontProperty(string propValue, Dictionary <string, string> properties)
        {
            int    mustBePos;
            string mustBe = RegexParserUtils.Search(RegexParserUtils.CssFontSizeAndLineHeight, propValue, out mustBePos);

            if (!string.IsNullOrEmpty(mustBe))
            {
                mustBe = mustBe.Trim();
                //Check for style||variant||weight on the left
                string leftSide    = propValue.Substring(0, mustBePos);
                string fontStyle   = RegexParserUtils.Search(RegexParserUtils.CssFontStyle, leftSide);
                string fontVariant = RegexParserUtils.Search(RegexParserUtils.CssFontVariant, leftSide);
                string fontWeight  = RegexParserUtils.Search(RegexParserUtils.CssFontWeight, leftSide);

                //Check for family on the right
                string rightSide  = propValue.Substring(mustBePos + mustBe.Length);
                string fontFamily = rightSide.Trim(); //Parser.Search(Parser.CssFontFamily, rightSide); //TODO: Would this be right?

                //Check for font-size and line-height
                string fontSize   = mustBe;
                string lineHeight = string.Empty;

                if (mustBe.Contains("/") && mustBe.Length > mustBe.IndexOf("/", StringComparison.Ordinal) + 1)
                {
                    int slashPos = mustBe.IndexOf("/", StringComparison.Ordinal);
                    fontSize   = mustBe.Substring(0, slashPos);
                    lineHeight = mustBe.Substring(slashPos + 1);
                }

                if (!string.IsNullOrEmpty(fontFamily))
                {
                    properties["font-family"] = ParseFontFamilyProperty(fontFamily);
                }
                if (!string.IsNullOrEmpty(fontStyle))
                {
                    properties["font-style"] = fontStyle;
                }
                if (!string.IsNullOrEmpty(fontVariant))
                {
                    properties["font-variant"] = fontVariant;
                }
                if (!string.IsNullOrEmpty(fontWeight))
                {
                    properties["font-weight"] = fontWeight;
                }
                if (!string.IsNullOrEmpty(fontSize))
                {
                    properties["font-size"] = fontSize;
                }
                if (!string.IsNullOrEmpty(lineHeight))
                {
                    properties["line-height"] = lineHeight;
                }
            }
            else
            {
                // Check for: caption | icon | menu | message-box | small-caption | status-bar
                //TODO: Interpret font values of: caption | icon | menu | message-box | small-caption | status-bar
            }
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Parse given stylesheet for media CSS blocks<br/>
        /// This blocks are added under the specific media block they are found.
        /// </summary>
        /// <param name="cssData">the CSS data to fill with parsed CSS objects</param>
        /// <param name="atrule">the @media rule to parse</param>
        private void ParseMediaAtRule(CssData cssData, string atrule)
        {
            //Extract specified media types
            MatchCollection types = RegexParserUtils.Match(RegexParserUtils.CssMediaTypes, atrule);

            if (types.Count == 1)
            {
                string line = types[0].Value;

                //Get blocks inside the at-rule
                var insideBlocks = RegexParserUtils.Match(RegexParserUtils.CssBlocks, atrule);

                //Get specified media types in the at-rule
                string[] mediaTypes = line.Substring(6, line.Length - 7).Split(_cssWhitespace, StringSplitOptions.RemoveEmptyEntries);

                //Scan media types
                foreach (string mediaType in mediaTypes)
                {
                    //Scan blocks and feed them to the style sheet
                    foreach (Match insideBlock in insideBlocks)
                    {
                        FeedStyleBlock(cssData, insideBlock.Value, mediaType);
                    }
                }
            }
        }
Ejemplo n.º 3
0
        /// <summary>
        /// Parse imports and return urls to imported stylesheets
        /// </summary>
        /// <param name="stylesheet">The stylesheet to parse</param>
        /// <returns>CSS imports</returns>
        private List <string> ParseImportStatement(string stylesheet)
        {
            int             startIdx          = 0;
            List <string>   imports           = new List <string>(1);
            MatchCollection importsCollection = RegexParserUtils.Match(RegexParserUtils.CssImportRule, stylesheet);

            foreach (Match import in importsCollection)
            {
                string importValue = import.Value;

                int urlStartIdx = importValue.IndexOf("url(", StringComparison.InvariantCultureIgnoreCase);

                if (urlStartIdx >= 0)
                {
                    urlStartIdx += 4;
                    int urlEndIdx = importValue.IndexOf(')', urlStartIdx);

                    if (urlEndIdx > -1)
                    {
                        urlEndIdx -= 1;
                        while (urlStartIdx < urlEndIdx && (char.IsWhiteSpace(importValue[urlStartIdx]) || importValue[urlStartIdx] == '\'' || importValue[urlStartIdx] == '"'))
                        {
                            urlStartIdx++;
                        }
                        while (urlStartIdx < urlEndIdx && (char.IsWhiteSpace(importValue[urlEndIdx]) || importValue[urlEndIdx] == '\'' || importValue[urlEndIdx] == '"'))
                        {
                            urlEndIdx--;
                        }

                        if (urlStartIdx <= urlEndIdx)
                        {
                            string url = importValue.Substring(urlStartIdx, urlEndIdx - urlStartIdx + 1);
                            imports.Add(url);
                        }
                    }
                }
                else
                {
                    urlStartIdx = importValue.IndexOf('"');
                    urlStartIdx = urlStartIdx == -1 ? importValue.IndexOf('\'') : urlStartIdx;

                    if (urlStartIdx >= 0)
                    {
                        int urlEndIdx = importValue.LastIndexOf('"');
                        urlEndIdx = urlEndIdx == -1 ? importValue.IndexOf('\'') : urlEndIdx;

                        string url = importValue.Substring(urlStartIdx + 1, urlEndIdx - urlStartIdx - 1);
                        imports.Add(url);
                    }
                }
            }

            return(imports);
        }
Ejemplo n.º 4
0
        private void ParsePageAtRule(CssData cssData, string atrule)
        {
            //Get blocks inside the at-rule
            var insideBlocks = RegexParserUtils.Match(RegexParserUtils.CssBlocks, atrule);
            // TODO: add page rules

            int    startIdx = 0;
            string nestedAtrule;

            while ((nestedAtrule = RegexParserUtils.GetCssAtRules(atrule, ref startIdx)) != null)
            {
                // TODO: add margin box rules
            }
        }
Ejemplo n.º 5
0
        /// <summary>
        /// Parse given stylesheet for media CSS blocks<br/>
        /// This blocks are added under the specific media block they are found.
        /// </summary>
        /// <param name="cssData">the CSS data to fill with parsed CSS objects</param>
        /// <param name="stylesheet">the stylesheet to parse</param>
        private void ParseAtRuleBlocks(CssData cssData, string stylesheet)
        {
            int    startIdx = 0;
            string atrule;

            while ((atrule = RegexParserUtils.GetCssAtRules(stylesheet, ref startIdx)) != null)
            {
                //Just process @media rules
                if (atrule.StartsWith("@media", StringComparison.InvariantCultureIgnoreCase))
                {
                    ParseMediaAtRule(cssData, atrule);
                }
                else if (atrule.StartsWith("@page", StringComparison.InvariantCultureIgnoreCase))
                {
                    ParsePageAtRule(cssData, atrule);
                }
            }
        }
Ejemplo n.º 6
0
        /// <summary>
        /// Parse given stylesheet for media CSS blocks<br/>
        /// This blocks are added under the specific media block they are found.
        /// </summary>
        /// <param name="cssData">the CSS data to fill with parsed CSS objects</param>
        /// <param name="stylesheet">the stylesheet to parse</param>
        private void ParseMediaStyleBlocks(CssData cssData, string stylesheet)
        {
            int    startIdx = 0;
            string atrule;

            while ((atrule = RegexParserUtils.GetCssAtRules(stylesheet, ref startIdx)) != null)
            {
                //Just process @media rules
                if (!atrule.StartsWith("@media", StringComparison.InvariantCultureIgnoreCase))
                {
                    continue;
                }

                //Extract specified media types
                MatchCollection types = RegexParserUtils.Match(RegexParserUtils.CssMediaTypes, atrule);

                if (types.Count == 1)
                {
                    string line = types[0].Value;

                    if (line.StartsWith("@media", StringComparison.InvariantCultureIgnoreCase) && line.EndsWith("{"))
                    {
                        //Get specified media types in the at-rule
                        string[] media = line.Substring(6, line.Length - 7).Split(' ');

                        //Scan media types
                        foreach (string t in media)
                        {
                            if (!String.IsNullOrEmpty(t.Trim()))
                            {
                                //Get blocks inside the at-rule
                                var insideBlocks = RegexParserUtils.Match(RegexParserUtils.CssBlocks, atrule);

                                //Scan blocks and feed them to the style sheet
                                foreach (Match insideBlock in insideBlocks)
                                {
                                    FeedStyleBlock(cssData, insideBlock.Value, t.Trim());
                                }
                            }
                        }
                    }
                }
            }
        }