public override void ExitRelativeFont(OrdinaryFormParser.RelativeFontContext context)
        {
            var kind = (FontType)_tokens.GetNumber(context.Kind);

            RelativeFont font;

            switch (kind)
            {
            case FontType.AutoFont:
                font = ParseAutoFont(context);
                break;

            case FontType.WindowsFont:
                font = ParseWindowsFont(context);
                break;

            case FontType.StyleItem:
                font = ParseStyleItem(context);
                break;

            default:
                return;
            }

            _values.Put(context.Parent, font);
        }
        private AutoFont ParseAutoFont(OrdinaryFormParser.RelativeFontContext context)
        {
            var font = new AutoFont();

            FillRelativeFont(font, context);

            return(font);
        }
        private WindowsFont ParseWindowsFont(OrdinaryFormParser.RelativeFontContext context)
        {
            var fontStyle = context.fontStyle();
            var style     = (WindowsFontStyle)_tokens.GetNumber(fontStyle.Value);

            var font = new WindowsFont
            {
                Style = style,
            };

            FillRelativeFont(font, context);

            return(font);
        }
        private RelativeFont ParseStyleItem(OrdinaryFormParser.RelativeFontContext context)
        {
            var fontStyle = context.fontStyle();
            var style     = _tokens.GetNumber(fontStyle.Value);

            RelativeFont font = style switch
            {
                0 => ParseFontFromConfiguration(fontStyle),
                _ => ParseStandardFont(style),
            };

            FillRelativeFont(font, context);

            return(font);
        }
        internal virtual void FillRelativeFont(
            RelativeFont font,
            OrdinaryFormParser.RelativeFontContext context)
        {
            var mask = (FontMask)_tokens.GetNumber(context.Mask);

            var optionalValueSequence = new[]
            {
                FontMask.Size,
                FontMask.Bold,
                FontMask.Italic,
                FontMask.Underline,
                FontMask.Strikeout,
            };

            var offset = 3;

            foreach (var flag in optionalValueSequence)
            {
                if ((mask & flag) == 0)
                {
                    continue;
                }

                var node  = context.NUMBER(offset);
                var value = _tokens.GetNumber(node);

                switch (flag)
                {
                case FontMask.Size:
                    font.Size = ParseSize(value);
                    break;

                case FontMask.Bold:
                    font.Bold = ParseBold(value);
                    break;

                case FontMask.Italic:
                    font.Italic = ParseBoolean(value);
                    break;

                case FontMask.Underline:
                    font.Underline = ParseBoolean(value);
                    break;

                case FontMask.Strikeout:
                    font.Strikeout = ParseBoolean(value);
                    break;

                default:
                    break;
                }

                offset++;
            }

            if ((mask & FontMask.FaceName) != 0)
            {
                font.FaceName = _tokens.GetString(context.FaceName);
            }

            font.Scale = (ushort)_tokens.GetNumber(context.Scale);
        }