Ejemplo n.º 1
0
        PdfTilingPattern BuildPattern(ImageBrush brush, XMatrix transform)
        {
            // Bounding box lays always at (0,0)
            XRect   bbox   = new XRect(0, 0, brush.Viewport.Width, brush.Viewport.Height);
            XMatrix matrix = transform;

            matrix.Prepend(new XMatrix(1, 0, 0, 1, brush.Viewport.X, brush.Viewport.Y));
            if (brush.Transform != null)
            {
                matrix.Prepend(new XMatrix(brush.Transform.Matrix.m11, brush.Transform.Matrix.m12, brush.Transform.Matrix.m21,
                                           brush.Transform.Matrix.m22, brush.Transform.Matrix.offsetX, brush.Transform.Matrix.offsetY));
            }

            // HACK by [email protected]
            // Avoid extra thin lines at the right and at the bottom of original image
            double xStep = brush.Viewport.Width + 1;
            double yStep = brush.Viewport.Height + 1;

            PdfTilingPattern pattern = Context.PdfDocument.Internals.CreateIndirectObject <PdfTilingPattern>();

            pattern.Elements.SetInteger(PdfTilingPattern.Keys.PatternType, 1); // Tiling
            pattern.Elements.SetInteger(PdfTilingPattern.Keys.PaintType, 1);   // Color
            pattern.Elements.SetInteger(PdfTilingPattern.Keys.TilingType, 3);  // Constant spacing and faster tiling
            pattern.Elements.SetMatrix(PdfTilingPattern.Keys.Matrix, matrix);
            pattern.Elements.SetRectangle(PdfTilingPattern.Keys.BBox, new PdfRectangle(bbox));
            pattern.Elements.SetReal(PdfTilingPattern.Keys.XStep, xStep);
            pattern.Elements.SetReal(PdfTilingPattern.Keys.YStep, yStep);

            // Set extended graphic state like Acrobat do
            PdfExtGState pdfExtGState = Context.PdfDocument.Internals.CreateIndirectObject <PdfExtGState>();

            pdfExtGState.SetDefault1();

            PdfFormXObject pdfForm = BuildForm(brush);

            PdfContentWriter writer = new PdfContentWriter(Context, pattern);

            writer.BeginContentRaw();

            // Acrobat 8 clips to bounding box, so do we
            //writer.WriteClip(bbox);

            XMatrix transformation = new XMatrix();
            double  dx             = brush.Viewport.Width / brush.Viewbox.Width * 96 / pdfForm.DpiX;
            double  dy             = brush.Viewport.Height / brush.Viewbox.Height * 96 / pdfForm.DpiY;

            transformation = new XMatrix(dx, 0, 0, dy, 0, 0);
            writer.WriteMatrix(transformation);
            writer.WriteGraphicsState(pdfExtGState);

            string name = writer.Resources.AddForm(pdfForm);

            writer.WriteLiteral(name + " Do\n");

            writer.EndContent();

            return(pattern);
        }
        public void RealizeBrush(XBrush brush, PdfColorMode colorMode, int renderingMode, double fontEmSize, bool isForPen = false)
        {
            // Rendering mode 2 is used for bold simulation.
            // Reference: TABLE 5.3  Text rendering modes / Page 402

            XSolidBrush solidBrush = brush as XSolidBrush;

            if (solidBrush != null)
            {
                XColor color     = solidBrush.Color;
                bool   overPrint = solidBrush.Overprint;

                if (renderingMode == 0)
                {
                    RealizeFillColor(color, overPrint, colorMode);
                }
                else if (renderingMode == 2)
                {
                    // Come here in case of bold simulation.
                    RealizeFillColor(color, false, colorMode);
                    //color = XColors.Green;
                    RealizePen(new XPen(color, fontEmSize * Const.BoldEmphasis), colorMode);
                }
                else
                {
                    throw new InvalidOperationException("Only rendering modes 0 and 2 are currently supported.");
                }
            }
            else
            {
                if (renderingMode != 0)
                {
                    throw new InvalidOperationException("Rendering modes other than 0 can only be used with solid color brushes.");
                }

                if (brush is XBaseGradientBrush gradientBrush)
                {
                    Debug.Assert(UnrealizedCtm.IsIdentity, "Must realize ctm first.");
                    XMatrix matrix = _renderer.DefaultViewMatrix;
                    matrix.Prepend(EffectiveCtm);
                    PdfShadingPattern pattern = new PdfShadingPattern(_renderer.Owner);
                    pattern.SetupFromBrush(gradientBrush, matrix, _renderer);
                    string name = _renderer.Resources.AddPattern(pattern);
                    if (isForPen)
                    {
                        _renderer.AppendFormatString("/Pattern CS\n", name);
                        _renderer.AppendFormatString("{0} SCN\n", name);
                    }
                    else
                    {
                        _renderer.AppendFormatString("/Pattern cs\n", name);
                        _renderer.AppendFormatString("{0} scn\n", name);
                    }
                    // Invalidate fill color.
                    _realizedFillColor = XColor.Empty;
                }
            }
        }
        public void RealizeBrush(XBrush brush, PdfColorMode colorMode)
        {
            if (brush is XSolidBrush)
            {
                XColor color = ((XSolidBrush)brush).Color;
                color = ColorSpaceHelper.EnsureColorMode(colorMode, color);

                if (colorMode != PdfColorMode.Cmyk)
                {
                    if (this.realizedFillColor.Rgb != color.Rgb)
                    {
                        this.renderer.Append(PdfEncoders.ToString(color, PdfColorMode.Rgb));
                        this.renderer.Append(" rg\n");
                    }
                }
                else
                {
                    if (!ColorSpaceHelper.IsEqualCmyk(this.realizedFillColor, color))
                    {
                        this.renderer.Append(PdfEncoders.ToString(color, PdfColorMode.Cmyk));
                        this.renderer.Append(" k\n");
                    }
                }

                if (this.renderer.Owner.Version >= 14 && this.realizedFillColor.A != color.A)
                {
                    PdfExtGState extGState = this.renderer.Owner.ExtGStateTable.GetExtGStateNonStroke(color.A);
                    string       gs        = this.renderer.Resources.AddExtGState(extGState);
                    this.renderer.AppendFormat("{0} gs\n", gs);

                    // Must create transparany group
                    if (this.renderer.page != null && color.A < 1)
                    {
                        this.renderer.page.transparencyUsed = true;
                    }
                }
                this.realizedFillColor = color;
            }
            else if (brush is XLinearGradientBrush)
            {
                XMatrix matrix = this.renderer.defaultViewMatrix;
                matrix.Prepend(this.Transform);
                PdfShadingPattern pattern = new PdfShadingPattern(this.renderer.Owner);
                pattern.SetupFromBrush((XLinearGradientBrush)brush, matrix);
                string name = this.renderer.Resources.AddPattern(pattern);
                this.renderer.AppendFormat("/Pattern cs\n", name);
                this.renderer.AppendFormat("{0} scn\n", name);

                // Invalidate fill color
                this.realizedFillColor = XColor.Empty;
            }
        }
Ejemplo n.º 4
0
        /// <summary>
        /// Realizes the CTM.
        /// </summary>
        public void RealizeCtm()
        {
            if (MustRealizeCtm)
            {
                Debug.Assert(!unrealizedCtm.IsIdentity, "mrCtm is unnecessarily set.");

                double[] matrix = unrealizedCtm.GetElements();
                // Up to six decimal digits to prevent round up problems
                renderer.AppendFormat("{0:0.######} {1:0.######} {2:0.######} {3:0.######} {4:0.######} {5:0.######} cm\n",
                                      matrix[0], matrix[1], matrix[2], matrix[3], matrix[4], matrix[5]);

                realizedCtm.Prepend(unrealizedCtm);
                unrealizedCtm  = new XMatrix(); //XMatrix.Identity;
                MustRealizeCtm = false;
            }
        }
Ejemplo n.º 5
0
        ///// <summary>
        ///// The world transform in PDF world space.
        ///// </summary>
        //public XMatrix EffectiveCtm
        //{
        //  get
        //  {
        //    //if (MustRealizeCtm)
        //    if (!UnrealizedCtm.IsIdentity)
        //    {
        //      XMatrix matrix = RealizedCtm;
        //      matrix.Prepend(UnrealizedCtm);
        //      return matrix;
        //    }
        //    return RealizedCtm;
        //  }
        //  //set
        //  //{
        //  //  XMatrix matrix = realizedCtm;
        //  //  matrix.Invert();
        //  //  matrix.Prepend(value);
        //  //  unrealizedCtm = matrix;
        //  //  MustRealizeCtm = !unrealizedCtm.IsIdentity;
        //  //}
        //}

        public void AddTransform(XMatrix value, XMatrixOrder matrixOrder)
        {
            // TODO: User matrixOrder
//#if DEBUG
//            if (matrixOrder == XMatrixOrder.Append)
//                throw new NotImplementedException("XMatrixOrder.Append");
//#endif
            XMatrix transform = value;

            if (_renderer.Gfx.PageDirection == XPageDirection.Downwards)
            {
                // Take chirality into account and
                // invert the direction of rotation.
                transform.M12 = -value.M12;
                transform.M21 = -value.M21;
            }
            UnrealizedCtm.Prepend(transform);

            WorldTransform.Prepend(value);
        }
Ejemplo n.º 6
0
        /// <summary>
        /// Realizes the CTM.
        /// </summary>
        public void RealizeCtm()
        {
            //if (MustRealizeCtm)
            if (!UnrealizedCtm.IsIdentity)
            {
                Debug.Assert(!UnrealizedCtm.IsIdentity, "mrCtm is unnecessarily set.");

                const string format = Config.SignificantFigures7;

                double[] matrix = UnrealizedCtm.GetElements();
                // Use up to six decimal digits to prevent round up problems.
                _renderer.AppendFormatArgs("{0:" + format + "} {1:" + format + "} {2:" + format + "} {3:" + format + "} {4:" + format + "} {5:" + format + "} cm\n",
                                           matrix[0], matrix[1], matrix[2], matrix[3], matrix[4], matrix[5]);

                RealizedCtm.Prepend(UnrealizedCtm);
                UnrealizedCtm       = new XMatrix();
                EffectiveCtm        = RealizedCtm;
                InverseEffectiveCtm = EffectiveCtm;
                InverseEffectiveCtm.Invert();
            }
        }
Ejemplo n.º 7
0
 public void Prepend(AbstractMatrix m)
 {
     matrix.Prepend(m.matrix);
 }
Ejemplo n.º 8
0
        PdfTilingPattern BuildPattern(ImageBrush brush, XMatrix transform)
        {
            // Bounding box lays always at (0,0)
            XRect bbox = new XRect(0, 0, brush.Viewport.Width, brush.Viewport.Height);

#if true
            XMatrix matrix = transform;
            matrix.Prepend(new XMatrix(1, 0, 0, 1, brush.Viewport.X, brush.Viewport.Y));
            if (brush.Transform != null)
            {
                matrix.Prepend(new XMatrix(brush.Transform.Matrix.m11, brush.Transform.Matrix.m12, brush.Transform.Matrix.m21,
                                           brush.Transform.Matrix.m22, brush.Transform.Matrix.offsetX, brush.Transform.Matrix.offsetY));
            }
#else
            double  c      = 1;
            XMatrix matrix = new XMatrix(1 * c, 0, 0, 1 * c, brush.Viewport.X * c, brush.Viewport.Y * c); // HACK: 480
            XMatrix t      = transform;
            //t.Invert();
            t.Prepend(matrix);
            //t.TranslateAppend(brush.Viewport.X , brush.Viewport.Y);
            //matrix.Append(t);
            matrix = t;
#endif
            double xStep = brush.Viewport.Width;
            double yStep = brush.Viewport.Height;

            // PdfTilingPattern
            //<<
            //  /BBox [0 0 240 120]
            //  /Length 74
            //  /Matrix [0.75 0 0 -0.75 0 480]
            //  /PaintType 1
            //  /PatternType 1
            //  /Resources
            //  <<
            //    /ExtGState
            //    <<
            //      /GS0 10 0 R
            //    >>
            //    /XObject
            //    <<
            //      /Fm0 17 0 R
            //    >>
            //  >>
            //  /TilingType 3
            //  /Type /Pattern
            //  /XStep 480
            //  /YStep 640
            //>>
            //stream
            //  q
            //  0 0 240 120 re
            //  W n
            //  q
            //    2.3999939 0 0 1.1999969 0 0 cm
            //    /GS0 gs
            //    /Fm0 Do
            //  Q
            //Q
            //endstream
            PdfTilingPattern pattern = Context.PdfDocument.Internals.CreateIndirectObject <PdfTilingPattern>();
            pattern.Elements.SetInteger(PdfTilingPattern.Keys.PatternType, 1); // Tiling
            pattern.Elements.SetInteger(PdfTilingPattern.Keys.PaintType, 1);   // Color
            pattern.Elements.SetInteger(PdfTilingPattern.Keys.TilingType, 3);  // Constant spacing and faster tiling
            pattern.Elements.SetMatrix(PdfTilingPattern.Keys.Matrix, matrix);
            pattern.Elements.SetRectangle(PdfTilingPattern.Keys.BBox, new PdfRectangle(bbox));
            pattern.Elements.SetReal(PdfTilingPattern.Keys.XStep, xStep);
            pattern.Elements.SetReal(PdfTilingPattern.Keys.YStep, yStep);

            // Set extended graphic state like Acrobat do
            PdfExtGState pdfExtGState = Context.PdfDocument.Internals.CreateIndirectObject <PdfExtGState>();
            pdfExtGState.SetDefault1();

            PdfFormXObject pdfForm = BuildForm(brush);
            //XRect viewBoxForm = new XRect(0, 0, 640, 480);

            PdfContentWriter writer = new PdfContentWriter(Context, pattern);
            writer.BeginContentRaw();

            // Acrobat 8 clips to bounding box, so do we
            //writer.WriteClip(bbox);

            XMatrix transformation = new XMatrix();
            double  dx             = brush.Viewport.Width / brush.Viewbox.Width * 96 / pdfForm.DpiX;
            double  dy             = brush.Viewport.Height / brush.Viewbox.Height * 96 / pdfForm.DpiY;
            transformation = new XMatrix(dx, 0, 0, dy, 0, 0);
            writer.WriteMatrix(transformation);
            writer.WriteGraphicsState(pdfExtGState);

            string name = writer.Resources.AddForm(pdfForm);
            writer.WriteLiteral(name + " Do\n");

            writer.EndContent();

            return(pattern);
        }
        PdfTilingPattern BuildPattern(VisualBrush brush, XMatrix transform)
        {
            // Bounding box lays always at (0,0)
            XRect bbox = new XRect(0, 0, brush.Viewport.Width, brush.Viewport.Height);

            XMatrix matrix = transform;

            matrix.Prepend(new XMatrix(1, 0, 0, 1, brush.Viewport.X, brush.Viewport.Y));
            if (brush.Transform != null)
            {
                matrix.Prepend(new XMatrix(brush.Transform.Value.M11, brush.Transform.Value.M12,
                                           brush.Transform.Value.M21, brush.Transform.Value.M22,
                                           brush.Transform.Value.OffsetX, brush.Transform.Value.OffsetY));
            }

            // Set X Step beyond the viewport if tilemode is set to none since
            // there is no other easy way to turn off tiling - NPJ
            double xStep = brush.Viewport.Width * (brush.TileMode == TileMode.None ? 2 : 1);
            double yStep = brush.Viewport.Height * (brush.TileMode == TileMode.None ? 2 : 1);

            // PdfTilingPattern
            //<<
            //  /BBox [0 0 240 120]
            //  /Length 74
            //  /Matrix [0.75 0 0 -0.75 0 480]
            //  /PaintType 1
            //  /PatternType 1
            //  /Resources
            //  <<
            //    /ExtGState
            //    <<
            //      /GS0 10 0 R
            //    >>
            //    /XObject
            //    <<
            //      /Fm0 17 0 R
            //    >>
            //  >>
            //  /TilingType 3
            //  /Type /Pattern
            //  /XStep 480
            //  /YStep 640
            //>>
            //stream
            //  q
            //  0 0 240 120 re
            //  W n
            //  q
            //    2.3999939 0 0 1.1999969 0 0 cm
            //    /GS0 gs
            //    /Fm0 Do
            //  Q
            //Q
            //endstream
            var pattern = new PdfTilingPattern(Context.PdfDocument);

            Context.PdfDocument.Internals.AddObject(pattern);
            pattern.Elements.SetInteger(PdfTilingPattern.Keys.PatternType, 1); // Tiling
            pattern.Elements.SetInteger(PdfTilingPattern.Keys.PaintType, 1);   // Color
            pattern.Elements.SetInteger(PdfTilingPattern.Keys.TilingType, 3);  // Constant spacing and faster tiling
            pattern.Elements.SetMatrix(PdfTilingPattern.Keys.Matrix, matrix);
            pattern.Elements.SetRectangle(PdfTilingPattern.Keys.BBox, new PdfRectangle(bbox));
            pattern.Elements.SetReal(PdfTilingPattern.Keys.XStep, xStep);
            pattern.Elements.SetReal(PdfTilingPattern.Keys.YStep, yStep);

            // Set extended graphic state like Acrobat do
            var pdfExtGState = Context.PdfDocument.Internals.CreateIndirectObject <PdfExtGState>();

            pdfExtGState.SetDefault1();

            var pdfForm = BuildForm(brush);

            var writer = new PdfContentWriter(Context, pattern);

            writer.BeginContentRaw();

            // Acrobat 8 clips to bounding box, so do we
            //writer.WriteClip(bbox);

            XMatrix transformation = new XMatrix();
            double  dx             = brush.Viewport.Width / brush.Viewbox.Width * 96 / pdfForm.DpiX;
            double  dy             = brush.Viewport.Height / brush.Viewbox.Height * 96 / pdfForm.DpiY;

            transformation = new XMatrix(dx, 0, 0, dy, 0, 0);
            writer.WriteMatrix(transformation);
            writer.WriteGraphicsState(pdfExtGState);

            string name = writer.Resources.AddForm(pdfForm);

            writer.WriteLiteral(name + " Do\n");

            writer.EndContent();

            return(pattern);
        }
Ejemplo n.º 10
0
        PdfTilingPattern BuildPattern(ImageBrush brush, XMatrix transform)
        {
            // Bounding box repects viewbox
            //XRect bbox = new XRect(brush.Viewbox.X, brush.Viewbox.Y, brush.Viewbox.Width, brush.Viewbox.Height);
            // double scalex = brush.Viewport.Width / brush.Viewbox.Width * 96 / pdfForm.DpiX;
            //BitmapImage src = new BitmapImage();
            //BitmapSource cropbrush = BitmapSource.Create()
            //CroppedBitmap cropbrush = new CroppedBitmap((BitmapSource)brush.ImageSource, new System.Windows.Int32Rect((int)brush.Viewbox.X, (int)brush.Viewbox.Y, (int)brush.Viewbox.Width, (int)brush.Viewbox.Height));
            //using (var fileStream = new System.IO.FileStream("c:\\fullimage.png", System.IO.FileMode.Create))
            //{
            //    BitmapEncoder encoder = new PngBitmapEncoder();
            //    encoder.Frames.Add(BitmapFrame.Create((BitmapSource)brush.ImageSource));
            //    encoder.Save(fileStream);
            //}
            double scaledpix = ((BitmapSource)brush.ImageSource).DpiX;
            double scaledpiy = ((BitmapSource)brush.ImageSource).DpiY;

            if (brush.Viewbox.X > 0 || brush.Viewbox.Y > 0)
            {
                CroppedBitmap cropbrush = new CroppedBitmap((BitmapSource)brush.ImageSource, new System.Windows.Int32Rect((int)Math.Round((brush.Viewbox.X / 96) * scaledpix), (int)Math.Round((brush.Viewbox.Y / 96) * scaledpiy), (int)Math.Round((brush.Viewbox.Width / 96) * scaledpiy), (int)Math.Round((brush.Viewbox.Height / 96) * scaledpiy)));
                //cropbrush.DpiX = scaledpix;
                //cropbrush.DpiY = scaledpiy;
                brush.ImageSource = cropbrush;
                //brush.Viewport = new System.Windows.Rect(0, 0, brush.Viewport.Width, brush.Viewport.Height);
                //brush.Viewbox = new System.Windows.Rect(0, 0, ((Math.Round((brush.Viewbox.Width / 96) * scaledpiy)) / scaledpiy * 96) , brush.Viewbox.Height);
                brush.Viewbox = new System.Windows.Rect(0, 0, brush.Viewbox.Width, brush.Viewbox.Height);
            }

            //brush = new ImageBrush(cropbrush);

            //BitmapSource
            //BitmapSource. cropbrushbitmap = new BitmapSource(cropbrush);


            //using (var fileStream = new System.IO.FileStream("c:\\cropimage.png", System.IO.FileMode.Create))
            //{
            //   BitmapEncoder encoder = new PngBitmapEncoder();
            //   encoder.Frames.Add(BitmapFrame.Create(cropbrush));
            //   encoder.Save(fileStream);
            //}

            //XRect bbox = new XRect(brush.Viewport.X - brush.Viewbox.X, brush.Viewport.Y - brush.Viewbox.Y, brush.Viewbox.Width, brush.Viewbox.Height);
            //XRect bbox = new XRect((brush.Viewbox.X / 96) * scaledpix, (brush.Viewbox.Y / 96) * scaledpiy, (brush.Viewbox.Width / 96) * scaledpix, (brush.Viewbox.Height / 96) * scaledpiy);
            //XRect bbox = new XRect(0, 0, (brush.Viewport.Width / 96) * scaledpix, (brush.Viewport.Height / 96) * scaledpiy);
            XRect bbox = new XRect(0, 0, brush.Viewport.Width, brush.Viewport.Height);

#if true
            XMatrix matrix = transform;
//this only needs to be a translate and to offset the viewbox viewport difference
            matrix.TranslatePrepend(brush.Viewport.X, brush.Viewport.Y);
            //matrix.TranslatePrepend((brush.Viewport.X - brush.Viewbox.X)+2, (brush.Viewport.Y - brush.Viewbox.Y)+2);

            if (brush.Transform != null)
            {
                matrix.Prepend(new XMatrix(brush.Transform.Value.M11, brush.Transform.Value.M12, brush.Transform.Value.M21,
                                           brush.Transform.Value.M22, brush.Transform.Value.OffsetX,
                                           brush.Transform.Value.OffsetY));
            }
#else
            double  c      = 1;
            XMatrix matrix = new XMatrix(1 * c, 0, 0, 1 * c, brush.Viewport.X * c, brush.Viewport.Y * c); // HACK: 480
            XMatrix t      = transform;
            //t.Invert();
            t.Prepend(matrix);
            //t.TranslateAppend(brush.Viewport.X , brush.Viewport.Y);
            //matrix.Append(t);
            matrix = t;
#endif
            double xStep = brush.Viewport.Width + 1;  // (brush.Viewbox.Width / 96) * scaledpix; //* (brush.TileMode == TileMode.None ? 2 : 1);
            double yStep = brush.Viewport.Height + 1; // (brush.Viewbox.Height / 96) * scaledpiy; //* (brush.TileMode == TileMode.None ? 2 : 1);


            // PdfTilingPattern
            //<<
            //  /BBox [0 0 240 120]
            //  /Length 74
            //  /Matrix [0.75 0 0 -0.75 0 480]
            //  /PaintType 1
            //  /PatternType 1
            //  /Resources
            //  <<
            //    /ExtGState
            //    <<
            //      /GS0 10 0 R
            //    >>
            //    /XObject
            //    <<
            //      /Fm0 17 0 R
            //    >>
            //  >>
            //  /TilingType 3
            //  /Type /Pattern
            //  /XStep 480
            //  /YStep 640
            //>>
            //stream
            //  q
            //  0 0 240 120 re
            //  W n
            //  q
            //    2.3999939 0 0 1.1999969 0 0 cm
            //    /GS0 gs
            //    /Fm0 Do
            //  Q
            //Q
            //endstream
            PdfTilingPattern pattern = Context.PdfDocument.Internals.CreateIndirectObject <PdfTilingPattern>();
            pattern.Elements.SetInteger(PdfTilingPattern.Keys.PatternType, 1); // Tiling
            pattern.Elements.SetInteger(PdfTilingPattern.Keys.PaintType, 1);   // Color
            pattern.Elements.SetInteger(PdfTilingPattern.Keys.TilingType, 3);  // Constant spacing and faster tiling
            pattern.Elements.SetMatrix(PdfTilingPattern.Keys.Matrix, matrix);
            pattern.Elements.SetRectangle(PdfTilingPattern.Keys.BBox, new PdfRectangle(bbox));
            pattern.Elements.SetReal(PdfTilingPattern.Keys.XStep, xStep);
            pattern.Elements.SetReal(PdfTilingPattern.Keys.YStep, yStep);

            // Set extended graphic state like Acrobat do
            PdfExtGState pdfExtGState = Context.PdfDocument.Internals.CreateIndirectObject <PdfExtGState>();
            pdfExtGState.SetDefault1();

            PdfFormXObject pdfForm = BuildForm(brush);
            //XRect viewBoxForm = new XRect(0, 0, 640, 480);

            PdfContentWriter writer = new PdfContentWriter(Context, pattern);
            writer.BeginContentRaw();

            // Acrobat 8 clips to bounding box, so do we
            //writer.WriteClip(bbox);

            XMatrix transformation = new XMatrix();
            //double dx = brush.Viewport.Width / brush.Viewbox.Width * 96 / pdfForm.DpiX;
            //double dy = brush.Viewport.Height / brush.Viewbox.Height * 96 / pdfForm.DpiY;

            double dx = brush.Viewport.Width / brush.Viewbox.Width * 96 / pdfForm.DpiX;
            double dy = brush.Viewport.Height / brush.Viewbox.Height * 96 / pdfForm.DpiY;
            transformation = new XMatrix(dx, 0, 0, dy, 0, 0);
            writer.WriteMatrix(transformation);
            writer.WriteGraphicsState(pdfExtGState);

            string name = writer.Resources.AddForm(pdfForm);
            writer.WriteLiteral(name + " Do\n");

            writer.EndContent();

            return(pattern);
        }