git-svn-id: https://pdfsharp.svn.codeplex.com/svn@39620 56d0cb2f-6006-4f69-a5a2-94740...
[pdfsharp:pdfsharp.git] / PDFsharp / code / PdfSharp / PdfSharp.Drawing / XGraphics.cs
1 #region PDFsharp - A .NET library for processing PDF\r
2 //\r
3 // Authors:\r
4 //   Stefan Lange (mailto:Stefan.Lange@pdfsharp.com)\r
5 //\r
6 // Copyright (c) 2005-2009 empira Software GmbH, Cologne (Germany)\r
7 //\r
8 // http://www.pdfsharp.com\r
9 // http://sourceforge.net/projects/pdfsharp\r
10 //\r
11 // Permission is hereby granted, free of charge, to any person obtaining a\r
12 // copy of this software and associated documentation files (the "Software"),\r
13 // to deal in the Software without restriction, including without limitation\r
14 // the rights to use, copy, modify, merge, publish, distribute, sublicense,\r
15 // and/or sell copies of the Software, and to permit persons to whom the\r
16 // Software is furnished to do so, subject to the following conditions:\r
17 //\r
18 // The above copyright notice and this permission notice shall be included\r
19 // in all copies or substantial portions of the Software.\r
20 //\r
21 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\r
22 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\r
23 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL\r
24 // THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\r
25 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING\r
26 // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER \r
27 // DEALINGS IN THE SOFTWARE.\r
28 #endregion\r
29 \r
30 using System;\r
31 using System.Diagnostics;\r
32 using System.Globalization;\r
33 using System.IO;\r
34 #if GDI\r
35 using System.Drawing;\r
36 using System.Drawing.Drawing2D;\r
37 using System.Drawing.Imaging;\r
38 #endif\r
39 #if WPF\r
40 using System.Windows;\r
41 using System.Windows.Media;\r
42 #endif\r
43 using PdfSharp.Internal;\r
44 using PdfSharp.Pdf;\r
45 using PdfSharp.Drawing.Pdf;\r
46 using PdfSharp.Pdf.Advanced;\r
47 \r
48 // ReSharper disable RedundantNameQualifier\r
49 namespace PdfSharp.Drawing\r
50 {\r
51   /// <summary>\r
52   /// Represents a drawing surface (or canvas) for a fixed size page.\r
53   /// </summary>\r
54   public sealed class XGraphics : IDisposable\r
55   {\r
56 #if GDI\r
57     /// <summary>\r
58     /// Initializes a new instance of the XGraphics class.\r
59     /// </summary>\r
60     /// <param name="gfx">The gfx.</param>\r
61     /// <param name="size">The size.</param>\r
62     /// <param name="pageUnit">The page unit.</param>\r
63     /// <param name="pageDirection">The page direction.</param>\r
64     XGraphics(Graphics gfx, XSize size, XGraphicsUnit pageUnit, XPageDirection pageDirection)\r
65     {\r
66       if (gfx == null)\r
67       {\r
68         //throw new ArgumentNullException("gfx");\r
69         gfx = Graphics.FromHwnd(IntPtr.Zero);\r
70       }\r
71 \r
72       this.gsStack = new GraphicsStateStack(this);\r
73       this.targetContext = XGraphicTargetContext.GDI;\r
74       this.gfx = gfx;\r
75       this.drawGraphics = true;\r
76       this.pageSize = new XSize(size.width, size.height);\r
77       this.pageUnit = pageUnit;\r
78       switch (pageUnit)\r
79       {\r
80         case XGraphicsUnit.Point:\r
81           this.pageSizePoints = new XSize(size.width, size.height);\r
82           break;\r
83 \r
84         case XGraphicsUnit.Inch:\r
85           this.pageSizePoints = new XSize(XUnit.FromInch(size.width), XUnit.FromInch(size.height));\r
86           break;\r
87 \r
88         case XGraphicsUnit.Millimeter:\r
89           this.pageSizePoints = new XSize(XUnit.FromMillimeter(size.width), XUnit.FromMillimeter(size.height));\r
90           break;\r
91 \r
92         case XGraphicsUnit.Centimeter:\r
93           this.pageSizePoints = new XSize(XUnit.FromCentimeter(size.width), XUnit.FromCentimeter(size.height));\r
94           break;\r
95 \r
96         default:\r
97           throw new NotImplementedException("unit");\r
98       }\r
99 \r
100       this.pageDirection = pageDirection;\r
101       Initialize();\r
102     }\r
103 #endif\r
104 \r
105 #if WPF && !SILVERLIGHT\r
106     /// <summary>\r
107     /// Initializes a new instance of the XGraphics class.\r
108     /// </summary>\r
109     /// <param name="dc">The drawing context.</param>\r
110     /// <param name="size">The size.</param>\r
111     /// <param name="pageUnit">The page unit.</param>\r
112     /// <param name="pageDirection">The page direction.</param>\r
113     XGraphics(DrawingContext dc, XSize size, XGraphicsUnit pageUnit, XPageDirection pageDirection)\r
114     {\r
115       if (dc == null)\r
116       {\r
117         //throw new ArgumentNullException("dc");\r
118         this.dv = new DrawingVisual();\r
119         dc = this.dv.RenderOpen();\r
120       }\r
121 \r
122       this.gsStack = new GraphicsStateStack(this);\r
123       this.targetContext = XGraphicTargetContext.WPF;\r
124       this.dc = dc;\r
125       this.drawGraphics = true;\r
126       this.pageSize = new XSize(size.width, size.height);\r
127       this.pageUnit = pageUnit;\r
128       switch (pageUnit)\r
129       {\r
130         case XGraphicsUnit.Point:\r
131           this.pageSizePoints = new XSize(size.width, size.height);\r
132           break;\r
133 \r
134         case XGraphicsUnit.Inch:\r
135           this.pageSizePoints = new XSize(XUnit.FromInch(size.width), XUnit.FromInch(size.height));\r
136           break;\r
137 \r
138         case XGraphicsUnit.Millimeter:\r
139           this.pageSizePoints = new XSize(XUnit.FromMillimeter(size.width), XUnit.FromMillimeter(size.height));\r
140           break;\r
141 \r
142         case XGraphicsUnit.Centimeter:\r
143           this.pageSizePoints = new XSize(XUnit.FromCentimeter(size.width), XUnit.FromCentimeter(size.height));\r
144           break;\r
145 \r
146         default:\r
147           throw new NotImplementedException("unit");\r
148       }\r
149 \r
150       this.pageDirection = pageDirection;\r
151       Initialize();\r
152     }\r
153 #endif\r
154 \r
155     /// <summary>\r
156     /// Initializes a new instance of the XGraphics class for drawing on a PDF page.\r
157     /// </summary>\r
158     XGraphics(PdfPage page, XGraphicsPdfPageOptions options, XGraphicsUnit pageUnit, XPageDirection pageDirection)\r
159     {\r
160       if (page == null)\r
161         throw new ArgumentNullException("page");\r
162 \r
163       if (page.Owner == null)\r
164         throw new ArgumentException("You cannot draw on a page that is not owned by a PdfDocument object.", "page");\r
165 \r
166       if (page.RenderContent != null)\r
167         throw new InvalidOperationException("An XGraphics object already exists for this page and must be disposed before a new one can be created.");\r
168 \r
169       if (page.Owner.IsReadOnly)\r
170         throw new InvalidOperationException("Cannot create XGraphics for a page of a document that cannot be modified. Use PdfDocumentOpenMode.Modify.");\r
171 \r
172       this.gsStack = new GraphicsStateStack(this);\r
173       PdfContent content = null;\r
174       switch (options)\r
175       {\r
176         case XGraphicsPdfPageOptions.Replace:\r
177           page.Contents.Elements.Clear();\r
178           goto case XGraphicsPdfPageOptions.Append;\r
179 \r
180         case XGraphicsPdfPageOptions.Prepend:\r
181           content = page.Contents.PrependContent();\r
182           break;\r
183 \r
184         case XGraphicsPdfPageOptions.Append:\r
185           content = page.Contents.AppendContent();\r
186           break;\r
187       }\r
188       page.RenderContent = content;\r
189 \r
190 #if GDI\r
191       // HACK: \r
192       this.gfx = Graphics.FromHwnd(IntPtr.Zero);\r
193       this.targetContext = XGraphicTargetContext.GDI;\r
194       //Bitmap bm = new Bitmap(10, 10);\r
195       //this.gfx = Graphics.FromImage(bm);\r
196 #endif\r
197 #if WPF\r
198 #if !SILVERLIGHT\r
199       this.dv = new DrawingVisual();\r
200       this.dc = this.dv.RenderOpen();\r
201       this.targetContext = XGraphicTargetContext.WPF;\r
202 #else\r
203       // AGHACK\r
204 #endif\r
205 #endif\r
206 #if GDI && WPF\r
207       this.targetContext = PdfSharp.Internal.TargetContextHelper.TargetContext;\r
208 #endif\r
209       this.renderer = new PdfSharp.Drawing.Pdf.XGraphicsPdfRenderer(page, this, options);\r
210       this.pageSizePoints = new XSize(page.Width, page.Height);\r
211       switch (pageUnit)\r
212       {\r
213         case XGraphicsUnit.Point:\r
214           this.pageSize = new XSize(page.Width, page.Height);\r
215           break;\r
216 \r
217         case XGraphicsUnit.Inch:\r
218           this.pageSize = new XSize(XUnit.FromPoint(page.Width).Inch, XUnit.FromPoint(page.Height).Inch);\r
219           break;\r
220 \r
221         case XGraphicsUnit.Millimeter:\r
222           this.pageSize = new XSize(XUnit.FromPoint(page.Width).Millimeter, XUnit.FromPoint(page.Height).Millimeter);\r
223           break;\r
224 \r
225         case XGraphicsUnit.Centimeter:\r
226           this.pageSize = new XSize(XUnit.FromPoint(page.Width).Centimeter, XUnit.FromPoint(page.Height).Centimeter);\r
227           break;\r
228 \r
229         default:\r
230           throw new NotImplementedException("unit");\r
231       }\r
232       this.pageUnit = pageUnit;\r
233       this.pageDirection = pageDirection;\r
234 \r
235       Initialize();\r
236     }\r
237 \r
238     /// <summary>\r
239     /// Initializes a new instance of the XGraphics class used for drawing on a form.\r
240     /// </summary>\r
241     XGraphics(XForm form)\r
242     {\r
243       if (form == null)\r
244         throw new ArgumentNullException("form");\r
245 \r
246       this.form = form;\r
247       form.AssociateGraphics(this);\r
248 \r
249       this.gsStack = new GraphicsStateStack(this);\r
250 #if GDI && !WPF\r
251       this.targetContext = XGraphicTargetContext.GDI;\r
252       // If form.Owner is null create a meta file.\r
253       if (form.Owner == null)\r
254       {\r
255         MemoryStream stream = new MemoryStream();\r
256         Graphics refgfx = Graphics.FromHwnd(IntPtr.Zero);\r
257         IntPtr hdc = refgfx.GetHdc();\r
258 \r
259 #if true_\r
260         // This code comes from my C++ RenderContext and checks some confusing details in connection \r
261         // with metafiles.\r
262         //                                                                                    Display                 | LaserJet\r
263         //                                                                               DPI   96 : 120               | 300\r
264         // physical device size in MM                                                    ---------------------------------------------\r
265         int horzSizeMM    = NativeMethods.GetDeviceCaps(hdc, NativeMethods.HORZSIZE);    // = 360 : 360               | 198 (not 210)\r
266         int vertSizeMM    = NativeMethods.GetDeviceCaps(hdc, NativeMethods.VERTSIZE);    // = 290 : 290               | 288 (hot 297)\r
267         // Cool:\r
268         // My monitor is a Sony SDM-N80 and it's size is EXACTLY 360mm x 290mm!!\r
269         // It is an 18.1" Flat Panel LCD display from 2002 and these are the values\r
270         // an older display drivers reports in about 2003:\r
271         //        Display  \r
272         //  DPI   96 : 120\r
273         //  --------------\r
274         //       330 : 254\r
275         //       254 : 203\r
276         // Obviously my ATI driver reports the exact size of the monitor.\r
277 \r
278 \r
279         // device size in pixel\r
280         int horzSizePixel = NativeMethods.GetDeviceCaps(hdc, NativeMethods.HORZRES);     // = 1280 : 1280             | 4676\r
281         int vertSizePixel = NativeMethods.GetDeviceCaps(hdc, NativeMethods.VERTRES);     // = 1024 : 1024             | 6814\r
282 \r
283         // 'logical' device resolution in DPI\r
284         int logResX       = NativeMethods.GetDeviceCaps(hdc, NativeMethods.LOGPIXELSX);  // = 96 : 120                | 600\r
285         int logResY       = NativeMethods.GetDeviceCaps(hdc, NativeMethods.LOGPIXELSY);  // = 96 : 120                | 600\r
286 \r
287         // now we can get the 'physical' device resolution...\r
288         float phyResX = horzSizePixel / (horzSizeMM / 25.4f);  // = 98.521210 : 128.00000   | 599.85052\r
289         float phyResY = vertSizePixel / (vertSizeMM / 25.4f);  // = 102.40000 : 128.12611   | 600.95691\r
290 \r
291         // ...and rescale the size of the meta rectangle.\r
292         float magicX = logResX / phyResX;                      // = 0.97440946 : 0.93750000 | 1.0002491\r
293         float magicY = logResY / phyResY;                      // = 0.93750000 : 0.93657720 | 0.99840766\r
294 \r
295         // use A4 page in point\r
296         // adjust size of A4 page so that meta file fits with DrawImage...\r
297         //RectangleF rcMagic = new RectangleF(0, 0, magicX * form.Width, magicY * form.Height);\r
298         //m_PreviewMetafile = new Metafile(hdc, rcMagic, MetafileFrameUnitPoint,\r
299         //  EmfTypeEmfPlusOnly, L"some description");\r
300 #endif\r
301 \r
302         RectangleF rect = new RectangleF(0, 0, form.PixelWidth, form.PixelHeight);\r
303         this.metafile = new Metafile(stream, hdc, rect, MetafileFrameUnit.Pixel); //, EmfType.EmfPlusOnly);\r
304 \r
305         // Petzold disposes the refgfx object, although the hdc is in use of the metafile\r
306         refgfx.ReleaseHdc(hdc);\r
307         refgfx.Dispose();\r
308 \r
309         this.gfx = Graphics.FromImage(this.metafile);\r
310         this.gfx.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.AntiAlias;\r
311         this.drawGraphics = true;\r
312       }\r
313       else\r
314       {\r
315         this.metafile = null;\r
316         this.gfx = Graphics.FromHwnd(IntPtr.Zero);\r
317       }\r
318       if (form.Owner != null)\r
319         this.renderer = new PdfSharp.Drawing.Pdf.XGraphicsPdfRenderer(form, this);\r
320       this.pageSize = form.Size;\r
321       Initialize();\r
322 #endif\r
323 #if WPF && !GDI\r
324 #if !SILVERLIGHT\r
325       this.targetContext = XGraphicTargetContext.WPF;\r
326       // If form.Owner is null create a meta file.\r
327       if (form.Owner == null)\r
328       {\r
329         this.dv = new DrawingVisual();\r
330         this.dc = this.dv.RenderOpen();\r
331         this.drawGraphics = true;\r
332       }\r
333       else\r
334       {\r
335         this.dv = new DrawingVisual();\r
336         this.dc = this.dv.RenderOpen();\r
337       }\r
338       if (form.Owner != null)\r
339         this.renderer = new PdfSharp.Drawing.Pdf.XGraphicsPdfRenderer(form, this);\r
340       this.pageSize = form.Size;\r
341       Initialize();\r
342 #else\r
343       // AGHACK\r
344 #endif\r
345 #endif\r
346     }\r
347 \r
348     /// <summary>\r
349     /// Creates the measure context. This is a graphics context created only for querying measures of text.\r
350     /// Drawing on a measure context has no effect.\r
351     /// </summary>\r
352     public static XGraphics CreateMeasureContext(XSize size, XGraphicsUnit pageUnit, XPageDirection pageDirection)\r
353     {\r
354       XGraphics gfx = null;\r
355 #if GDI\r
356       gfx = new XGraphics((System.Drawing.Graphics)null, size, pageUnit, pageDirection);\r
357 #endif\r
358 #if WPF\r
359 #if !SILVERLIGHT\r
360       gfx = new XGraphics((System.Windows.Media.DrawingContext)null, size, pageUnit, pageDirection);\r
361 #else\r
362       // AGHACK\r
363 #endif\r
364 #endif\r
365       return gfx;\r
366     }\r
367 \r
368 #if GDI\r
369     /// <summary>\r
370     /// Creates a new instance of the XGraphics class from a System.Drawing.Graphics object.\r
371     /// </summary>\r
372     public static XGraphics FromGraphics(Graphics graphics, XSize size)\r
373     {\r
374       // TODO: Get object from cache...\r
375       return new XGraphics(graphics, size, XGraphicsUnit.Point, XPageDirection.Downwards);\r
376     }\r
377 \r
378     /// <summary>\r
379     /// Creates a new instance of the XGraphics class from a System.Drawing.Graphics object.\r
380     /// </summary>\r
381     public static XGraphics FromGraphics(Graphics graphics, XSize size, XGraphicsUnit unit)\r
382     {\r
383       // TODO: Get object from cache...\r
384       return new XGraphics(graphics, size, unit, XPageDirection.Downwards);\r
385     }\r
386 \r
387     ///// <summary>\r
388     ///// Creates a new instance of the XGraphics class from a System.Drawing.Graphics object.\r
389     ///// </summary>\r
390     //public static XGraphics FromGraphics(Graphics graphics, XSize size, XPageDirection pageDirection)\r
391     //{\r
392     //  // TODO: Get object from cache...\r
393     //  return new XGraphics(graphics, size, XGraphicsUnit.Point, pageDirection);\r
394     //}\r
395 \r
396     ///// <summary>\r
397     ///// Creates a new instance of the XGraphics class from a System.Drawing.Graphics object.\r
398     ///// </summary>\r
399     //public static XGraphics FromGraphics(Graphics graphics, XSize size, XGraphicsUnit unit, XPageDirection pageDirection)\r
400     //{\r
401     //  // TODO: Get object from cache...\r
402     //  return new XGraphics(graphics, size, XGraphicsUnit.Point, pageDirection);\r
403     //}\r
404 #endif\r
405 \r
406 #if WPF && !SILVERLIGHT\r
407     /// <summary>\r
408     /// Creates a new instance of the XGraphics class from a System.Windows.Media.DrawingContext object.\r
409     /// </summary>\r
410     public static XGraphics FromDrawingContext(DrawingContext drawingContext, XSize size, XGraphicsUnit unit)\r
411     {\r
412       return new XGraphics(drawingContext, size, unit, XPageDirection.Downwards);\r
413     }\r
414 #endif\r
415 \r
416     /// <summary>\r
417     /// Creates a new instance of the XGraphics class from a PdfSharp.Pdf.PdfPage object.\r
418     /// </summary>\r
419     public static XGraphics FromPdfPage(PdfPage page)\r
420     {\r
421       return new XGraphics(page, XGraphicsPdfPageOptions.Append, XGraphicsUnit.Point, XPageDirection.Downwards);\r
422     }\r
423 \r
424     /// <summary>\r
425     /// Creates a new instance of the XGraphics class from a PdfSharp.Pdf.PdfPage object.\r
426     /// </summary>\r
427     public static XGraphics FromPdfPage(PdfPage page, XGraphicsUnit unit)\r
428     {\r
429       return new XGraphics(page, XGraphicsPdfPageOptions.Append, unit, XPageDirection.Downwards);\r
430     }\r
431 \r
432     /// <summary>\r
433     /// Creates a new instance of the XGraphics class from a PdfSharp.Pdf.PdfPage object.\r
434     /// </summary>\r
435     public static XGraphics FromPdfPage(PdfPage page, XPageDirection pageDirection)\r
436     {\r
437       return new XGraphics(page, XGraphicsPdfPageOptions.Append, XGraphicsUnit.Point, pageDirection);\r
438     }\r
439 \r
440     /// <summary>\r
441     /// Creates a new instance of the XGraphics class from a PdfSharp.Pdf.PdfPage object.\r
442     /// </summary>\r
443     public static XGraphics FromPdfPage(PdfPage page, XGraphicsPdfPageOptions options)\r
444     {\r
445       return new XGraphics(page, options, XGraphicsUnit.Point, XPageDirection.Downwards);\r
446     }\r
447 \r
448     /// <summary>\r
449     /// Creates a new instance of the XGraphics class from a PdfSharp.Pdf.PdfPage object.\r
450     /// </summary>\r
451     public static XGraphics FromPdfPage(PdfPage page, XGraphicsPdfPageOptions options, XPageDirection pageDirection)\r
452     {\r
453       return new XGraphics(page, options, XGraphicsUnit.Point, pageDirection);\r
454     }\r
455 \r
456     /// <summary>\r
457     /// Creates a new instance of the XGraphics class from a PdfSharp.Pdf.PdfPage object.\r
458     /// </summary>\r
459     public static XGraphics FromPdfPage(PdfPage page, XGraphicsPdfPageOptions options, XGraphicsUnit unit)\r
460     {\r
461       return new XGraphics(page, options, unit, XPageDirection.Downwards);\r
462     }\r
463 \r
464     /// <summary>\r
465     /// Creates a new instance of the XGraphics class from a PdfSharp.Pdf.PdfPage object.\r
466     /// </summary>\r
467     public static XGraphics FromPdfPage(PdfPage page, XGraphicsPdfPageOptions options, XGraphicsUnit unit, XPageDirection pageDirection)\r
468     {\r
469       return new XGraphics(page, options, unit, pageDirection);\r
470     }\r
471 \r
472     /// <summary>\r
473     /// Creates a new instance of the XGraphics class from a PdfSharp.Drawing.XPdfForm object.\r
474     /// </summary>\r
475     public static XGraphics FromPdfForm(XPdfForm form)\r
476     {\r
477       if (form.gfx != null)\r
478         return form.gfx;\r
479 \r
480       return new XGraphics(form);\r
481     }\r
482 \r
483     /// <summary>\r
484     /// Creates a new instance of the XGraphics class from a PdfSharp.Drawing.XForm object.\r
485     /// </summary>\r
486     public static XGraphics FromForm(XForm form)\r
487     {\r
488       if (form.gfx != null)\r
489         return form.gfx;\r
490 \r
491       return new XGraphics(form);\r
492     }\r
493 \r
494     /// <summary>\r
495     /// Internal setup.\r
496     /// </summary>\r
497     void Initialize()\r
498     {\r
499       this.pageOrigin = new XPoint();\r
500       XMatrix matrix = new XMatrix();  //XMatrix.Identity;\r
501 \r
502       double pageHeight = this.pageSize.height;\r
503       PdfPage targetPage = PdfPage;\r
504       XPoint trimOffset = new XPoint();\r
505       if (targetPage != null && targetPage.TrimMargins.AreSet)\r
506       {\r
507         pageHeight += targetPage.TrimMargins.Top.Point + targetPage.TrimMargins.Bottom.Point;\r
508         trimOffset = new XPoint(targetPage.TrimMargins.Left.Point, targetPage.TrimMargins.Top.Point);\r
509       }\r
510 \r
511 #if GDI\r
512       if (this.targetContext == XGraphicTargetContext.GDI)\r
513       {\r
514         if (this.gfx != null)\r
515           matrix = (XMatrix)gfx.Transform;\r
516 \r
517         if (this.pageUnit != XGraphicsUnit.Point)\r
518         {\r
519           switch (this.pageUnit)\r
520           {\r
521             case XGraphicsUnit.Inch:\r
522               matrix.ScalePrepend(XUnit.InchFactor);\r
523               break;\r
524 \r
525             case XGraphicsUnit.Millimeter:\r
526               matrix.ScalePrepend(XUnit.MillimeterFactor);\r
527               break;\r
528 \r
529             case XGraphicsUnit.Centimeter:\r
530               matrix.ScalePrepend(XUnit.CentimeterFactor);\r
531               break;\r
532 \r
533             case XGraphicsUnit.Presentation:\r
534               matrix.ScalePrepend(XUnit.PresentationFactor);\r
535               break;\r
536           }\r
537         }\r
538       }\r
539 #endif\r
540 #if WPF\r
541       if (this.targetContext == XGraphicTargetContext.WPF)\r
542       {\r
543         if (this.pageUnit != XGraphicsUnit.Presentation)\r
544         {\r
545           switch (this.pageUnit)\r
546           {\r
547             case XGraphicsUnit.Point:\r
548               matrix.ScalePrepend(XUnit.PointFactorWpf);\r
549               break;\r
550 \r
551             case XGraphicsUnit.Inch:\r
552               matrix.ScalePrepend(XUnit.InchFactorWpf);\r
553               break;\r
554 \r
555             case XGraphicsUnit.Millimeter:\r
556               matrix.ScalePrepend(XUnit.MillimeterFactorWpf);\r
557               break;\r
558 \r
559             case XGraphicsUnit.Centimeter:\r
560               matrix.ScalePrepend(XUnit.CentimeterFactorWpf);\r
561               break;\r
562           }\r
563           if (!matrix.IsIdentity)\r
564           {\r
565 #if !SILVERLIGHT\r
566             MatrixTransform transform = new MatrixTransform((System.Windows.Media.Matrix)matrix);\r
567             dc.PushTransform(transform);\r
568 #else\r
569             // AGHACK\r
570 #endif\r
571           }\r
572         }\r
573       }\r
574 #endif\r
575 \r
576       if (this.pageDirection == XPageDirection.Upwards)\r
577         matrix.Prepend(new XMatrix(1, 0, 0, -1, 0, pageHeight));\r
578 \r
579       if (trimOffset != new XPoint())\r
580         matrix.TranslatePrepend(trimOffset.x, trimOffset.y);\r
581 \r
582       this.defaultViewMatrix = matrix;\r
583       this.transform = new XMatrix();  //XMatrix.Identity;\r
584     }\r
585 \r
586     /// <summary>\r
587     /// Releases all resources used by this object.\r
588     /// </summary>\r
589     public void Dispose()\r
590     {\r
591       Dispose(true);\r
592     }\r
593 \r
594     void Dispose(bool disposing)\r
595     {\r
596       if (!this.disposed)\r
597       {\r
598         this.disposed = true;\r
599         if (disposing)\r
600         {\r
601           // Dispose managed resources.\r
602         }\r
603 \r
604         if (this.form != null)\r
605           this.form.Finish();\r
606 \r
607 #if GDI\r
608         if (this.targetContext == XGraphicTargetContext.GDI)\r
609         {\r
610           // GDI+ requires this to disassociate it from metafiles\r
611           this.gfx.Dispose();\r
612           this.gfx = null;\r
613           this.metafile = null;\r
614         }\r
615 #endif\r
616 #if WPF\r
617 #if !SILVERLIGHT\r
618         if (this.dc != null)\r
619         {\r
620           this.dc.Close();\r
621           this.dv = null;\r
622         }\r
623 #else\r
624         // AGHACK\r
625 #endif\r
626 #endif\r
627         this.drawGraphics = false;\r
628 \r
629         if (this.renderer != null)\r
630         {\r
631           this.renderer.Close();\r
632           this.renderer = null;\r
633         }\r
634       }\r
635     }\r
636     bool disposed;\r
637 \r
638     /// <summary>\r
639     /// Internal hack for MigraDoc. Will be removed in further releases.\r
640     /// Unicode support requires a global refactoring of MigraDoc and will be done in further releases.\r
641     /// </summary>\r
642     public PdfFontEncoding MUH  // MigraDoc Unicode Hack...\r
643     {\r
644       get { return this.muh; }\r
645       set { this.muh = value; }\r
646     }\r
647     PdfFontEncoding muh;\r
648 \r
649     /// <summary>\r
650     /// Internal hack for MigraDoc. Will be removed in further releases.\r
651     /// Font embedding support requires a global refactoring of MigraDoc and will be done in further releases.\r
652     /// </summary>\r
653     public PdfFontEmbedding MFEH  // MigraDoc Font Embedding Hack...\r
654     {\r
655       get { return this.mfeh; }\r
656       set { this.mfeh = value; }\r
657     }\r
658     PdfFontEmbedding mfeh;\r
659 \r
660     /// <summary>\r
661     /// A value indicating whether GDI+ or WPF is used as context.\r
662     /// </summary>\r
663     internal XGraphicTargetContext targetContext;\r
664 \r
665     /// <summary>\r
666     /// Gets or sets the unit of measure used for page coordinates.\r
667     /// CURRENTLY ONLY POINT IS IMPLEMENTED.\r
668     /// </summary>\r
669     public XGraphicsUnit PageUnit\r
670     {\r
671       get { return this.pageUnit; }\r
672       //set\r
673       //{\r
674       //  // TODO: other page units\r
675       //  if (value != XGraphicsUnit.Point)\r
676       //    throw new NotImplementedException("PageUnit must be XGraphicsUnit.Point in current implementation.");\r
677       //}\r
678     }\r
679     XGraphicsUnit pageUnit;\r
680 \r
681     /// <summary>\r
682     /// Gets or sets the a value indicating in which direction y-value grow.\r
683     /// </summary>\r
684     public XPageDirection PageDirection\r
685     {\r
686       get { return this.pageDirection; }\r
687       set\r
688       {\r
689         //TODO\r
690         if (value != XPageDirection.Downwards)\r
691           throw new NotImplementedException("PageDirection must be XPageDirection.Downwards in current implementation.");\r
692       }\r
693     }\r
694     XPageDirection pageDirection;\r
695 \r
696     /// <summary>\r
697     /// Gets the current page origin. Setting the origin is not yet implemented.\r
698     /// </summary>\r
699     public XPoint PageOrigin\r
700     {\r
701       get { return this.pageOrigin; }\r
702       set\r
703       {\r
704         //TODO\r
705         if (value != new XPoint())\r
706           throw new NotImplementedException("PageOrigin cannot be modified in current implementation.");\r
707       }\r
708     }\r
709     XPoint pageOrigin;\r
710 \r
711     /// <summary>\r
712     /// Gets the current size of the page.\r
713     /// </summary>\r
714     public XSize PageSize\r
715     {\r
716       get { return this.pageSize; }\r
717       //set\r
718       //{\r
719       //  //TODO\r
720       //  throw new NotImplementedException("PageSize cannot be modified in current implementation.");\r
721       //}\r
722     }\r
723     XSize pageSize;\r
724     XSize pageSizePoints;\r
725 \r
726     //public void Flush();\r
727     //public void Flush(FlushIntention intention);\r
728 \r
729     #region Drawing\r
730 \r
731     // ----- Clear --------------------------------------------------------------------------------\r
732 \r
733     /// <summary>\r
734     /// Fills the entire drawing surface with the specified color. The functions works only if\r
735     /// the current transformation is identity, i.e. the function should be called only immediately\r
736     /// after the XGraphics object was created.\r
737     /// </summary>\r
738     public void Clear(XColor color)\r
739     {\r
740       if (this.drawGraphics)\r
741       {\r
742 #if GDI\r
743         if (this.targetContext == XGraphicTargetContext.GDI)\r
744           this.gfx.Clear(color.ToGdiColor());\r
745 #endif\r
746 #if WPF\r
747         if (this.targetContext == XGraphicTargetContext.WPF)\r
748         {\r
749           Rect rc = new Rect();\r
750           rc.Width = rc.Height = 10000;\r
751 #if !SILVERLIGHT\r
752           this.dc.DrawRectangle(new SolidColorBrush(color.ToWpfColor()), null, rc);\r
753 #else\r
754           // AGHACK\r
755 #endif\r
756         }\r
757 #endif\r
758       }\r
759 \r
760       if (this.renderer != null)\r
761         this.renderer.Clear(color);\r
762     }\r
763 \r
764     // ----- DrawLine -----------------------------------------------------------------------------\r
765 \r
766 #if GDI\r
767     /// <summary>\r
768     /// Draws a line connecting two Point structures.\r
769     /// </summary>\r
770     public void DrawLine(XPen pen, System.Drawing.Point pt1, System.Drawing.Point pt2)\r
771     {\r
772       DrawLine(pen, (double)pt1.X, (double)pt1.Y, (double)pt2.X, (double)pt2.Y);\r
773     }\r
774 #endif\r
775 \r
776 #if WPF\r
777     /// <summary>\r
778     /// Draws a line connecting two Point structures.\r
779     /// </summary>\r
780     public void DrawLine(XPen pen, System.Windows.Point pt1, System.Windows.Point pt2)\r
781     {\r
782       DrawLine(pen, (double)pt1.X, (double)pt1.Y, (double)pt2.X, (double)pt2.Y);\r
783     }\r
784 #endif\r
785 \r
786 #if GDI\r
787     /// <summary>\r
788     /// Draws a line connecting two PointF structures.\r
789     /// </summary>\r
790     public void DrawLine(XPen pen, PointF pt1, PointF pt2)\r
791     {\r
792       DrawLine(pen, pt1.X, pt1.Y, pt2.X, pt2.Y);\r
793     }\r
794 #endif\r
795 \r
796     /// <summary>\r
797     /// Draws a line connecting two XPoint structures.\r
798     /// </summary>\r
799     public void DrawLine(XPen pen, XPoint pt1, XPoint pt2)\r
800     {\r
801       DrawLine(pen, pt1.X, pt1.Y, pt2.X, pt2.Y);\r
802     }\r
803 \r
804     /// <summary>\r
805     /// Draws a line connecting the two points specified by coordinate pairs.\r
806     /// </summary>\r
807     public void DrawLine(XPen pen, int x1, int y1, int x2, int y2)\r
808     {\r
809       DrawLine(pen, (double)x1, (double)y1, (double)x2, (double)y2);\r
810     }\r
811 \r
812     /// <summary>\r
813     /// Draws a line connecting the two points specified by coordinate pairs.\r
814     /// </summary>\r
815     public void DrawLine(XPen pen, double x1, double y1, double x2, double y2)\r
816     {\r
817       if (pen == null)\r
818         throw new ArgumentNullException("pen");\r
819 \r
820       if (this.drawGraphics)\r
821       {\r
822 #if GDI\r
823         if (this.targetContext == XGraphicTargetContext.GDI)\r
824           this.gfx.DrawLine(pen.RealizeGdiPen(), (float)x1, (float)y1, (float)x2, (float)y2);\r
825 #endif\r
826 #if WPF\r
827 #if !SILVERLIGHT\r
828         if (this.targetContext == XGraphicTargetContext.WPF)\r
829           this.dc.DrawLine(pen.RealizeWpfPen(), new System.Windows.Point(x1, y1), new System.Windows.Point(x2, y2));\r
830 #else\r
831         // AGHACK\r
832 #endif\r
833 #endif\r
834       }\r
835 \r
836       if (this.renderer != null)\r
837         this.renderer.DrawLines(pen, new XPoint[2] { new XPoint(x1, y1), new XPoint(x2, y2) });\r
838     }\r
839 \r
840     // ----- DrawLines ----------------------------------------------------------------------------\r
841 \r
842 #if GDI\r
843     /// <summary>\r
844     /// Draws a series of line segments that connect an array of points.\r
845     /// </summary>\r
846     public void DrawLines(XPen pen, System.Drawing.Point[] points)\r
847     {\r
848       DrawLines(pen, MakePointFArray(points));\r
849     }\r
850 #endif\r
851 \r
852 #if WPF\r
853     /// <summary>\r
854     /// Draws a series of line segments that connect an array of points.\r
855     /// </summary>\r
856     public void DrawLines(XPen pen, System.Windows.Point[] points)\r
857     {\r
858       DrawLines(pen, XGraphics.MakeXPointArray(points));\r
859     }\r
860 #endif\r
861 \r
862 #if GDI\r
863     /// <summary>\r
864     /// Draws a series of line segments that connect an array of points.\r
865     /// </summary>\r
866     public void DrawLines(XPen pen, PointF[] points)\r
867     {\r
868       if (pen == null)\r
869         throw new ArgumentNullException("pen");\r
870       if (points == null)\r
871         throw new ArgumentNullException("points");\r
872       if (points.Length < 2)\r
873         throw new ArgumentException("points", PSSR.PointArrayAtLeast(2));\r
874 \r
875       if (this.drawGraphics)\r
876         this.gfx.DrawLines(pen.RealizeGdiPen(), points);\r
877 \r
878       if (this.renderer != null)\r
879         this.renderer.DrawLines(pen, MakeXPointArray(points));\r
880     }\r
881 #endif\r
882 \r
883     /// <summary>\r
884     /// Draws a series of line segments that connect an array of points.\r
885     /// </summary>\r
886     public void DrawLines(XPen pen, XPoint[] points)\r
887     {\r
888       if (pen == null)\r
889         throw new ArgumentNullException("pen");\r
890       if (points == null)\r
891         throw new ArgumentNullException("points");\r
892       if (points.Length < 2)\r
893         throw new ArgumentException("points", PSSR.PointArrayAtLeast(2));\r
894 \r
895       if (this.drawGraphics)\r
896       {\r
897 #if GDI\r
898         if (this.targetContext == XGraphicTargetContext.GDI)\r
899           this.gfx.DrawLines(pen.RealizeGdiPen(), XGraphics.MakePointFArray(points));\r
900 #endif\r
901 #if WPF\r
902         if (this.targetContext == XGraphicTargetContext.WPF)\r
903         {\r
904 #if !SILVERLIGHT\r
905           PolyLineSegment seg = new PolyLineSegment(XGraphics.MakePointArray(points), true);\r
906 #else\r
907           Point[] pts = XGraphics.MakePointArray(points);\r
908           PointCollection collection = new PointCollection();\r
909           foreach (Point point in pts)\r
910             collection.Add(point);\r
911           PolyLineSegment seg = new PolyLineSegment();\r
912           seg.Points = collection;\r
913 #endif\r
914           PathFigure figure = new PathFigure();\r
915           figure.StartPoint = new System.Windows.Point(points[0].x, points[0].y);\r
916           figure.Segments.Add(seg);\r
917           PathGeometry geo = new PathGeometry();\r
918           geo.Figures.Add(figure);\r
919           this.dc.DrawGeometry(null, pen.RealizeWpfPen(), geo);\r
920         }\r
921 #endif\r
922       }\r
923 \r
924       if (this.renderer != null)\r
925         this.renderer.DrawLines(pen, points);\r
926     }\r
927 \r
928     /// <summary>\r
929     /// Draws a series of line segments that connect an array of x and y pairs.\r
930     /// </summary>\r
931     public void DrawLines(XPen pen, double x, double y, params double[] value)\r
932     {\r
933       if (pen == null)\r
934         throw new ArgumentNullException("pen");\r
935       if (value == null)\r
936         throw new ArgumentNullException("value");\r
937 \r
938       int length = value.Length;\r
939       XPoint[] points = new XPoint[length / 2 + 1];\r
940       points[0].X = x;\r
941       points[0].Y = y;\r
942       for (int idx = 0; idx < length / 2; idx++)\r
943       {\r
944         points[idx + 1].X = value[2 * idx];\r
945         points[idx + 1].Y = value[2 * idx + 1];\r
946       }\r
947       DrawLines(pen, points);\r
948     }\r
949 \r
950     // ----- DrawBezier ---------------------------------------------------------------------------\r
951 \r
952 #if GDI\r
953     /// <summary>\r
954     /// Draws a Bézier spline defined by four points.\r
955     /// </summary>\r
956     public void DrawBezier(XPen pen, System.Drawing.Point pt1, System.Drawing.Point pt2, System.Drawing.Point pt3, System.Drawing.Point pt4)\r
957     {\r
958       DrawBezier(pen, (double)pt1.X, (double)pt1.Y, (double)pt2.X, (double)pt2.Y,\r
959         (double)pt3.X, (double)pt3.Y, (double)pt4.X, (double)pt4.Y);\r
960     }\r
961 #endif\r
962 \r
963 #if WPF\r
964     /// <summary>\r
965     /// Draws a Bézier spline defined by four points.\r
966     /// </summary>\r
967     public void DrawBezier(XPen pen, System.Windows.Point pt1, System.Windows.Point pt2, System.Windows.Point pt3, System.Windows.Point pt4)\r
968     {\r
969       DrawBezier(pen, (double)pt1.X, (double)pt1.Y, (double)pt2.X, (double)pt2.Y,\r
970         (double)pt3.X, (double)pt3.Y, (double)pt4.X, (double)pt4.Y);\r
971     }\r
972 #endif\r
973 \r
974 #if GDI\r
975     /// <summary>\r
976     /// Draws a Bézier spline defined by four points.\r
977     /// </summary>\r
978     public void DrawBezier(XPen pen, PointF pt1, PointF pt2, PointF pt3, PointF pt4)\r
979     {\r
980       DrawBezier(pen, pt1.X, pt1.Y, pt2.X, pt2.Y, pt3.X, pt3.Y, pt4.X, pt4.Y);\r
981     }\r
982 #endif\r
983 \r
984     /// <summary>\r
985     /// Draws a Bézier spline defined by four points.\r
986     /// </summary>\r
987     public void DrawBezier(XPen pen, XPoint pt1, XPoint pt2, XPoint pt3, XPoint pt4)\r
988     {\r
989       DrawBezier(pen, pt1.X, pt1.Y, pt2.X, pt2.Y, pt3.X, pt3.Y, pt4.X, pt4.Y);\r
990     }\r
991 \r
992     /// <summary>\r
993     /// Draws a Bézier spline defined by four points.\r
994     /// </summary>\r
995     public void DrawBezier(XPen pen, double x1, double y1, double x2, double y2,\r
996       double x3, double y3, double x4, double y4)\r
997     {\r
998       if (pen == null)\r
999         throw new ArgumentNullException("pen");\r
1000 \r
1001       if (this.drawGraphics)\r
1002       {\r
1003 #if GDI\r
1004         if (this.targetContext == XGraphicTargetContext.GDI)\r
1005           this.gfx.DrawBezier(pen.RealizeGdiPen(), (float)x1, (float)y1, (float)x2, (float)y2, (float)x3, (float)y3, (float)x4, (float)y4);\r
1006 #endif\r
1007 #if WPF\r
1008         if (this.targetContext == XGraphicTargetContext.WPF)\r
1009         {\r
1010 #if !SILVERLIGHT\r
1011           BezierSegment seg = new BezierSegment(new System.Windows.Point(x2, y2), new System.Windows.Point(x3, y3), new System.Windows.Point(x4, y4), true);\r
1012           PathFigure figure = new PathFigure();\r
1013           figure.StartPoint = new System.Windows.Point(x1, y1);\r
1014           figure.Segments.Add(seg);\r
1015           PathGeometry geo = new PathGeometry();\r
1016           geo.Figures.Add(figure);\r
1017           this.dc.DrawGeometry(null, pen.RealizeWpfPen(), geo);\r
1018 #endif\r
1019         }\r
1020 #endif\r
1021       }\r
1022 \r
1023       if (this.renderer != null)\r
1024         this.renderer.DrawBeziers(pen,\r
1025           new XPoint[4]{new XPoint(x1, y1), new XPoint(x2, y2), \r
1026           new XPoint(x3, y3), new XPoint(x4, y4)});\r
1027     }\r
1028 \r
1029     // ----- DrawBeziers --------------------------------------------------------------------------\r
1030 \r
1031 #if GDI\r
1032     /// <summary>\r
1033     /// Draws a series of Bézier splines from an array of points.\r
1034     /// </summary>\r
1035     public void DrawBeziers(XPen pen, System.Drawing.Point[] points)\r
1036     {\r
1037       DrawBeziers(pen, MakeXPointArray(points));\r
1038     }\r
1039 #endif\r
1040 \r
1041 #if WPF\r
1042     /// <summary>\r
1043     /// Draws a series of Bézier splines from an array of points.\r
1044     /// </summary>\r
1045     public void DrawBeziers(XPen pen, System.Windows.Point[] points)\r
1046     {\r
1047       DrawBeziers(pen, MakeXPointArray(points));\r
1048     }\r
1049 #endif\r
1050 \r
1051 #if GDI\r
1052     /// <summary>\r
1053     /// Draws a series of Bézier splines from an array of points.\r
1054     /// </summary>\r
1055     public void DrawBeziers(XPen pen, PointF[] points)\r
1056     {\r
1057       DrawBeziers(pen, MakeXPointArray(points));\r
1058     }\r
1059 #endif\r
1060 \r
1061     /// <summary>\r
1062     /// Draws a series of Bézier splines from an array of points.\r
1063     /// </summary>\r
1064     public void DrawBeziers(XPen pen, XPoint[] points)\r
1065     {\r
1066       if (pen == null)\r
1067         throw new ArgumentNullException("pen");\r
1068 \r
1069       int count = points.Length;\r
1070       if (count == 0)\r
1071         return;\r
1072 \r
1073       if ((count - 1) % 3 != 0)\r
1074         throw new ArgumentException("Invalid number of points for bezier curves. Number must fulfil 4+3n.", "points");\r
1075 \r
1076       if (this.drawGraphics)\r
1077       {\r
1078 #if GDI\r
1079         if (this.targetContext == XGraphicTargetContext.GDI)\r
1080           this.gfx.DrawBeziers(pen.RealizeGdiPen(), MakePointFArray(points));\r
1081 #endif\r
1082 #if WPF\r
1083         if (this.targetContext == XGraphicTargetContext.WPF)\r
1084         {\r
1085 #if !SILVERLIGHT\r
1086           PathFigure figure = new PathFigure();\r
1087           figure.StartPoint = new System.Windows.Point(points[0].x, points[0].y);\r
1088           for (int idx = 1; idx < count; idx += 3)\r
1089           {\r
1090             BezierSegment seg = new BezierSegment(\r
1091               new System.Windows.Point(points[idx].x, points[idx].y),\r
1092               new System.Windows.Point(points[idx + 1].x, points[idx + 1].y),\r
1093               new System.Windows.Point(points[idx + 2].x, points[idx + 2].y), true);\r
1094             figure.Segments.Add(seg);\r
1095           }\r
1096           PathGeometry geo = new PathGeometry();\r
1097           geo.Figures.Add(figure);\r
1098           this.dc.DrawGeometry(null, pen.RealizeWpfPen(), geo);\r
1099 #endif\r
1100         }\r
1101 #endif\r
1102       }\r
1103 \r
1104       if (this.renderer != null)\r
1105         this.renderer.DrawBeziers(pen, points);\r
1106     }\r
1107 \r
1108     // ----- DrawCurve ----------------------------------------------------------------------------\r
1109 \r
1110 #if GDI\r
1111     /// <summary>\r
1112     /// Draws a cardinal spline through a specified array of points.\r
1113     /// </summary>\r
1114     public void DrawCurve(XPen pen, System.Drawing.Point[] points)\r
1115     {\r
1116       DrawCurve(pen, MakePointFArray(points), 0.5);\r
1117     }\r
1118 #endif\r
1119 \r
1120 #if WPF\r
1121     /// <summary>\r
1122     /// Draws a cardinal spline through a specified array of points.\r
1123     /// </summary>\r
1124     public void DrawCurve(XPen pen, System.Windows.Point[] points)\r
1125     {\r
1126       DrawCurve(pen, MakeXPointArray(points), 0.5);\r
1127     }\r
1128 #endif\r
1129 \r
1130 #if GDI\r
1131     /// <summary>\r
1132     /// Draws a cardinal spline through a specified array of points.\r
1133     /// </summary>\r
1134     public void DrawCurve(XPen pen, PointF[] points)\r
1135     {\r
1136       DrawCurve(pen, MakeXPointArray(points), 0.5);\r
1137     }\r
1138 #endif\r
1139 \r
1140     /// <summary>\r
1141     /// Draws a cardinal spline through a specified array of points.\r
1142     /// </summary>\r
1143     public void DrawCurve(XPen pen, XPoint[] points)\r
1144     {\r
1145       DrawCurve(pen, points, 0.5);\r
1146     }\r
1147 \r
1148 #if GDI\r
1149     /// <summary>\r
1150     /// Draws a cardinal spline through a specified array of points using a specified tension. \r
1151     /// </summary>\r
1152     public void DrawCurve(XPen pen, System.Drawing.Point[] points, double tension)\r
1153     {\r
1154       DrawCurve(pen, MakeXPointArray(points), tension);\r
1155     }\r
1156 #endif\r
1157 \r
1158 #if WPF\r
1159     /// <summary>\r
1160     /// Draws a cardinal spline through a specified array of points using a specified tension. \r
1161     /// </summary>\r
1162     public void DrawCurve(XPen pen, System.Windows.Point[] points, double tension)\r
1163     {\r
1164       DrawCurve(pen, MakeXPointArray(points), tension);\r
1165     }\r
1166 #endif\r
1167 \r
1168 #if GDI\r
1169     /// <summary>\r
1170     /// Draws a cardinal spline through a specified array of points using a specified tension. \r
1171     /// </summary>\r
1172     public void DrawCurve(XPen pen, PointF[] points, double tension)\r
1173     {\r
1174       DrawCurve(pen, MakeXPointArray(points), tension);\r
1175     }\r
1176 #endif\r
1177 \r
1178     /// <summary>\r
1179     /// Draws a cardinal spline through a specified array of points using a specified tension. \r
1180     /// </summary>\r
1181     public void DrawCurve(XPen pen, XPoint[] points, double tension)\r
1182     {\r
1183       if (pen == null)\r
1184         throw new ArgumentNullException("pen");\r
1185       if (points == null)\r
1186         throw new ArgumentNullException("points");\r
1187 \r
1188       int count = points.Length;\r
1189       if (count < 2)\r
1190         throw new ArgumentException("DrawCurve requires two or more points.", "points");\r
1191 \r
1192       if (this.drawGraphics)\r
1193       {\r
1194 #if GDI\r
1195         if (this.targetContext == XGraphicTargetContext.GDI)\r
1196           this.gfx.DrawCurve(pen.RealizeGdiPen(), MakePointFArray(points), (float)tension);\r
1197 #endif\r
1198 #if WPF\r
1199         if (this.targetContext == XGraphicTargetContext.WPF)\r
1200         {\r
1201           tension /= 3;\r
1202 \r
1203           PathFigure figure = new PathFigure();\r
1204           figure.StartPoint = new System.Windows.Point(points[0].x, points[0].y);\r
1205           if (count == 2)\r
1206           {\r
1207             figure.Segments.Add(GeometryHelper.CreateCurveSegment(points[0], points[0], points[1], points[1], tension));\r
1208           }\r
1209           else\r
1210           {\r
1211             figure.Segments.Add(GeometryHelper.CreateCurveSegment(points[0], points[0], points[1], points[2], tension));\r
1212             for (int idx = 1; idx < count - 2; idx++)\r
1213               figure.Segments.Add(GeometryHelper.CreateCurveSegment(points[idx - 1], points[idx], points[idx + 1], points[idx + 2], tension));\r
1214             figure.Segments.Add(GeometryHelper.CreateCurveSegment(points[count - 3], points[count - 2], points[count - 1], points[count - 1], tension));\r
1215           }\r
1216           PathGeometry geo = new PathGeometry();\r
1217           geo.Figures.Add(figure);\r
1218           this.dc.DrawGeometry(null, pen.RealizeWpfPen(), geo);\r
1219         }\r
1220 #endif\r
1221       }\r
1222 \r
1223       if (this.renderer != null)\r
1224         this.renderer.DrawCurve(pen, points, tension);\r
1225     }\r
1226 \r
1227     // TODO:\r
1228     //public void DrawCurve(XPen pen, PointF[] points, int offset, int numberOfSegments);\r
1229     //public void DrawCurve(XPen pen, Point[] points, int offset, int numberOfSegments, double tension);\r
1230     //public void DrawCurve(XPen pen, PointF[] points, int offset, int numberOfSegments, double tension);\r
1231 \r
1232     // ----- DrawArc ------------------------------------------------------------------------------\r
1233 \r
1234 #if GDI\r
1235     /// <summary>\r
1236     /// Draws an arc representing a portion of an ellipse.\r
1237     /// </summary>\r
1238     public void DrawArc(XPen pen, Rectangle rect, double startAngle, double sweepAngle)\r
1239     {\r
1240       DrawArc(pen, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height, startAngle, sweepAngle);\r
1241     }\r
1242 #endif\r
1243 \r
1244 #if GDI\r
1245     /// <summary>\r
1246     /// Draws an arc representing a portion of an ellipse.\r
1247     /// </summary>\r
1248     public void DrawArc(XPen pen, RectangleF rect, double startAngle, double sweepAngle)\r
1249     {\r
1250       DrawArc(pen, rect.X, rect.Y, rect.Width, rect.Height, startAngle, sweepAngle);\r
1251     }\r
1252 #endif\r
1253 \r
1254     /// <summary>\r
1255     /// Draws an arc representing a portion of an ellipse.\r
1256     /// </summary>\r
1257     public void DrawArc(XPen pen, XRect rect, double startAngle, double sweepAngle)\r
1258     {\r
1259       DrawArc(pen, rect.X, rect.Y, rect.Width, rect.Height, startAngle, sweepAngle);\r
1260     }\r
1261 \r
1262     /// <summary>\r
1263     /// Draws an arc representing a portion of an ellipse.\r
1264     /// </summary>\r
1265     public void DrawArc(XPen pen, int x, int y, int width, int height, int startAngle, int sweepAngle)\r
1266     {\r
1267       DrawArc(pen, (double)x, (double)y, (double)width, (double)height, startAngle, sweepAngle);\r
1268     }\r
1269 \r
1270     /// <summary>\r
1271     /// Draws an arc representing a portion of an ellipse.\r
1272     /// </summary>\r
1273     public void DrawArc(XPen pen, double x, double y, double width, double height, double startAngle, double sweepAngle)\r
1274     {\r
1275       if (pen == null)\r
1276         throw new ArgumentNullException("pen");\r
1277 \r
1278       if (Math.Abs(sweepAngle) >= 360)\r
1279       {\r
1280         DrawEllipse(pen, x, y, width, height);\r
1281       }\r
1282       else\r
1283       {\r
1284         if (this.drawGraphics)\r
1285         {\r
1286 #if GDI\r
1287           if (this.targetContext == XGraphicTargetContext.GDI)\r
1288             this.gfx.DrawArc(pen.RealizeGdiPen(), (float)x, (float)y, (float)width, (float)height, (float)startAngle, (float)sweepAngle);\r
1289 #endif\r
1290 #if WPF\r
1291           if (this.targetContext == XGraphicTargetContext.WPF)\r
1292           {\r
1293             System.Windows.Point startPoint;\r
1294             ArcSegment seg = GeometryHelper.CreateArcSegment(x, y, width, height, startAngle, sweepAngle, out startPoint);\r
1295             PathFigure figure = new PathFigure();\r
1296             figure.StartPoint = startPoint;\r
1297             figure.Segments.Add(seg);\r
1298             PathGeometry geo = new PathGeometry();\r
1299             geo.Figures.Add(figure);\r
1300             this.dc.DrawGeometry(null, pen.RealizeWpfPen(), geo);\r
1301           }\r
1302 #endif\r
1303         }\r
1304 \r
1305         if (this.renderer != null)\r
1306           this.renderer.DrawArc(pen, x, y, width, height, startAngle, sweepAngle);\r
1307       }\r
1308     }\r
1309 \r
1310     // ----- DrawRectangle ------------------------------------------------------------------------\r
1311 \r
1312     // ----- stroke -----\r
1313 \r
1314 #if GDI\r
1315     /// <summary>\r
1316     /// Draws a rectangle.\r
1317     /// </summary>\r
1318     public void DrawRectangle(XPen pen, Rectangle rect)\r
1319     {\r
1320       DrawRectangle(pen, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height);\r
1321     }\r
1322 #endif\r
1323 \r
1324 #if GDI\r
1325     /// <summary>\r
1326     /// Draws a rectangle.\r
1327     /// </summary>\r
1328     public void DrawRectangle(XPen pen, RectangleF rect)\r
1329     {\r
1330       DrawRectangle(pen, rect.X, rect.Y, rect.Width, rect.Height);\r
1331     }\r
1332 #endif\r
1333 \r
1334     /// <summary>\r
1335     /// Draws a rectangle.\r
1336     /// </summary>\r
1337     public void DrawRectangle(XPen pen, XRect rect)\r
1338     {\r
1339       DrawRectangle(pen, rect.X, rect.Y, rect.Width, rect.Height);\r
1340     }\r
1341 \r
1342     /// <summary>\r
1343     /// Draws a rectangle.\r
1344     /// </summary>\r
1345     public void DrawRectangle(XPen pen, int x, int y, int width, int height)\r
1346     {\r
1347       DrawRectangle(pen, (double)x, (double)y, (double)width, (double)height);\r
1348     }\r
1349 \r
1350     /// <summary>\r
1351     /// Draws a rectangle.\r
1352     /// </summary>\r
1353     public void DrawRectangle(XPen pen, double x, double y, double width, double height)\r
1354     {\r
1355       if (pen == null)\r
1356         throw new ArgumentNullException("pen");\r
1357 \r
1358       if (this.drawGraphics)\r
1359       {\r
1360 #if GDI\r
1361         if (this.targetContext == XGraphicTargetContext.GDI)\r
1362           this.gfx.DrawRectangle(pen.RealizeGdiPen(), (float)x, (float)y, (float)width, (float)height);\r
1363 #endif\r
1364 #if WPF\r
1365         if (this.targetContext == XGraphicTargetContext.WPF)\r
1366         {\r
1367 #if !SILVERLIGHT\r
1368           this.dc.DrawRectangle(null, pen.RealizeWpfPen(), new Rect(x, y, width, height));\r
1369 #endif\r
1370         }\r
1371 #endif\r
1372       }\r
1373 \r
1374       if (this.renderer != null)\r
1375         this.renderer.DrawRectangle(pen, null, x, y, width, height);\r
1376     }\r
1377 \r
1378     // ----- fill -----\r
1379 \r
1380 #if GDI\r
1381     /// <summary>\r
1382     /// Draws a rectangle.\r
1383     /// </summary>\r
1384     public void DrawRectangle(XBrush brush, Rectangle rect)\r
1385     {\r
1386       DrawRectangle(brush, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height);\r
1387     }\r
1388 #endif\r
1389 \r
1390 #if GDI\r
1391     /// <summary>\r
1392     /// Draws a rectangle.\r
1393     /// </summary>\r
1394     public void DrawRectangle(XBrush brush, RectangleF rect)\r
1395     {\r
1396       DrawRectangle(brush, rect.X, rect.Y, rect.Width, rect.Height);\r
1397     }\r
1398 #endif\r
1399 \r
1400     /// <summary>\r
1401     /// Draws a rectangle.\r
1402     /// </summary>\r
1403     public void DrawRectangle(XBrush brush, XRect rect)\r
1404     {\r
1405       DrawRectangle(brush, rect.X, rect.Y, rect.Width, rect.Height);\r
1406     }\r
1407 \r
1408     /// <summary>\r
1409     /// Draws a rectangle.\r
1410     /// </summary>\r
1411     public void DrawRectangle(XBrush brush, int x, int y, int width, int height)\r
1412     {\r
1413       DrawRectangle(brush, (double)x, (double)y, (double)width, (double)height);\r
1414     }\r
1415 \r
1416     /// <summary>\r
1417     /// Draws a rectangle.\r
1418     /// </summary>\r
1419     public void DrawRectangle(XBrush brush, double x, double y, double width, double height)\r
1420     {\r
1421       if (brush == null)\r
1422         throw new ArgumentNullException("brush");\r
1423 \r
1424       if (this.drawGraphics)\r
1425       {\r
1426 #if GDI\r
1427         if (this.targetContext == XGraphicTargetContext.GDI)\r
1428           this.gfx.FillRectangle(brush.RealizeGdiBrush(), (float)x, (float)y, (float)width, (float)height);\r
1429 #endif\r
1430 #if WPF\r
1431         if (this.targetContext == XGraphicTargetContext.WPF)\r
1432           this.dc.DrawRectangle(brush.RealizeWpfBrush(), null, new Rect(x, y, width, height));\r
1433 #endif\r
1434       }\r
1435 \r
1436       if (this.renderer != null)\r
1437         this.renderer.DrawRectangle(null, brush, x, y, width, height);\r
1438     }\r
1439 \r
1440     // ----- stroke and fill -----\r
1441 \r
1442 #if GDI\r
1443     /// <summary>\r
1444     /// Draws a rectangle.\r
1445     /// </summary>\r
1446     public void DrawRectangle(XPen pen, XBrush brush, Rectangle rect)\r
1447     {\r
1448       DrawRectangle(pen, brush, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height);\r
1449     }\r
1450 #endif\r
1451 \r
1452 #if GDI\r
1453     /// <summary>\r
1454     /// Draws a rectangle.\r
1455     /// </summary>\r
1456     public void DrawRectangle(XPen pen, XBrush brush, RectangleF rect)\r
1457     {\r
1458       DrawRectangle(pen, brush, rect.X, rect.Y, rect.Width, rect.Height);\r
1459     }\r
1460 #endif\r
1461 \r
1462     /// <summary>\r
1463     /// Draws a rectangle.\r
1464     /// </summary>\r
1465     public void DrawRectangle(XPen pen, XBrush brush, XRect rect)\r
1466     {\r
1467       DrawRectangle(pen, brush, rect.X, rect.Y, rect.Width, rect.Height);\r
1468     }\r
1469 \r
1470     /// <summary>\r
1471     /// Draws a rectangle.\r
1472     /// </summary>\r
1473     public void DrawRectangle(XPen pen, XBrush brush, int x, int y, int width, int height)\r
1474     {\r
1475       DrawRectangle(pen, brush, (double)x, (double)y, (double)width, (double)height);\r
1476     }\r
1477 \r
1478     /// <summary>\r
1479     /// Draws a rectangle.\r
1480     /// </summary>\r
1481     public void DrawRectangle(XPen pen, XBrush brush, double x, double y, double width, double height)\r
1482     {\r
1483       if (pen == null && brush == null)\r
1484         throw new ArgumentNullException("pen and brush", PSSR.NeedPenOrBrush);\r
1485 \r
1486       if (this.drawGraphics)\r
1487       {\r
1488 #if GDI\r
1489         if (this.targetContext == XGraphicTargetContext.GDI)\r
1490         {\r
1491           this.gfx.FillRectangle(brush.RealizeGdiBrush(), (float)x, (float)y, (float)width, (float)height);\r
1492           this.gfx.DrawRectangle(pen.RealizeGdiPen(), (float)x, (float)y, (float)width, (float)height);\r
1493         }\r
1494 #endif\r
1495 #if WPF\r
1496         if (this.targetContext == XGraphicTargetContext.WPF)\r
1497           this.dc.DrawRectangle(brush.RealizeWpfBrush(), pen.RealizeWpfPen(), new Rect(x, y, width, height));\r
1498 #endif\r
1499       }\r
1500 \r
1501       if (this.renderer != null)\r
1502         this.renderer.DrawRectangle(pen, brush, x, y, width, height);\r
1503     }\r
1504 \r
1505     // ----- DrawRectangles -----------------------------------------------------------------------\r
1506 \r
1507     // ----- stroke -----\r
1508 \r
1509 #if GDI\r
1510     /// <summary>\r
1511     /// Draws a series of rectangles.\r
1512     /// </summary>\r
1513     public void DrawRectangles(XPen pen, Rectangle[] rectangles)\r
1514     {\r
1515       if (pen == null)\r
1516         throw new ArgumentNullException("pen");\r
1517       if (rectangles == null)\r
1518         throw new ArgumentNullException("rectangles");\r
1519 \r
1520       DrawRectangles(pen, null, rectangles);\r
1521     }\r
1522 #endif\r
1523 \r
1524 #if GDI\r
1525     /// <summary>\r
1526     /// Draws a series of rectangles.\r
1527     /// </summary>\r
1528     public void DrawRectangles(XPen pen, RectangleF[] rectangles)\r
1529     {\r
1530       if (pen == null)\r
1531         throw new ArgumentNullException("pen");\r
1532       if (rectangles == null)\r
1533         throw new ArgumentNullException("rectangles");\r
1534 \r
1535       DrawRectangles(pen, null, rectangles);\r
1536     }\r
1537 #endif\r
1538 \r
1539     /// <summary>\r
1540     /// Draws a series of rectangles.\r
1541     /// </summary>\r
1542     public void DrawRectangles(XPen pen, XRect[] rectangles)\r
1543     {\r
1544       if (pen == null)\r
1545         throw new ArgumentNullException("pen");\r
1546       if (rectangles == null)\r
1547         throw new ArgumentNullException("rectangles");\r
1548 \r
1549       DrawRectangles(pen, null, rectangles);\r
1550     }\r
1551 \r
1552     // ----- fill -----\r
1553 \r
1554 #if GDI\r
1555     /// <summary>\r
1556     /// Draws a series of rectangles.\r
1557     /// </summary>\r
1558     public void DrawRectangles(XBrush brush, Rectangle[] rectangles)\r
1559     {\r
1560       if (brush == null)\r
1561         throw new ArgumentNullException("brush");\r
1562       if (rectangles == null)\r
1563         throw new ArgumentNullException("rectangles");\r
1564 \r
1565       DrawRectangles(null, brush, rectangles);\r
1566     }\r
1567 #endif\r
1568 \r
1569 #if GDI\r
1570     /// <summary>\r
1571     /// Draws a series of rectangles.\r
1572     /// </summary>\r
1573     public void DrawRectangles(XBrush brush, RectangleF[] rectangles)\r
1574     {\r
1575       if (brush == null)\r
1576         throw new ArgumentNullException("brush");\r
1577       if (rectangles == null)\r
1578         throw new ArgumentNullException("rectangles");\r
1579 \r
1580       DrawRectangles(null, brush, rectangles);\r
1581     }\r
1582 #endif\r
1583 \r
1584     /// <summary>\r
1585     /// Draws a series of rectangles.\r
1586     /// </summary>\r
1587     public void DrawRectangles(XBrush brush, XRect[] rectangles)\r
1588     {\r
1589       if (brush == null)\r
1590         throw new ArgumentNullException("brush");\r
1591       if (rectangles == null)\r
1592         throw new ArgumentNullException("rectangles");\r
1593 \r
1594       DrawRectangles(null, brush, rectangles);\r
1595     }\r
1596 \r
1597     // ----- stroke and fill -----\r
1598 \r
1599 #if GDI\r
1600     /// <summary>\r
1601     /// Draws a series of rectangles.\r
1602     /// </summary>\r
1603     public void DrawRectangles(XPen pen, XBrush brush, Rectangle[] rectangles)\r
1604     {\r
1605       if (pen == null && brush == null)\r
1606         throw new ArgumentNullException("pen and brush", PSSR.NeedPenOrBrush);\r
1607       if (rectangles == null)\r
1608         throw new ArgumentNullException("rectangles");\r
1609 \r
1610       if (this.drawGraphics)\r
1611       {\r
1612         this.gfx.FillRectangles(brush.RealizeGdiBrush(), rectangles);\r
1613         this.gfx.DrawRectangles(pen.RealizeGdiPen(), rectangles);\r
1614       }\r
1615       if (this.renderer != null)\r
1616       {\r
1617         int count = rectangles.Length;\r
1618         for (int idx = 0; idx < count; idx++)\r
1619         {\r
1620           Rectangle rect = rectangles[idx];\r
1621           this.renderer.DrawRectangle(pen, brush, rect.X, rect.Y, rect.Width, rect.Height);\r
1622         }\r
1623       }\r
1624     }\r
1625 #endif\r
1626 \r
1627 #if GDI\r
1628     /// <summary>\r
1629     /// Draws a series of rectangles.\r
1630     /// </summary>\r
1631     public void DrawRectangles(XPen pen, XBrush brush, RectangleF[] rectangles)\r
1632     {\r
1633       if (pen == null && brush == null)\r
1634         throw new ArgumentNullException("pen and brush", PSSR.NeedPenOrBrush);\r
1635       if (rectangles == null)\r
1636         throw new ArgumentNullException("rectangles");\r
1637 \r
1638       if (this.drawGraphics)\r
1639       {\r
1640         this.gfx.FillRectangles(brush.RealizeGdiBrush(), rectangles);\r
1641         this.gfx.DrawRectangles(pen.RealizeGdiPen(), rectangles);\r
1642       }\r
1643       if (this.renderer != null)\r
1644       {\r
1645         int count = rectangles.Length;\r
1646         for (int idx = 0; idx < count; idx++)\r
1647         {\r
1648           RectangleF rect = rectangles[idx];\r
1649           this.renderer.DrawRectangle(pen, brush, rect.X, rect.Y, rect.Width, rect.Height);\r
1650         }\r
1651       }\r
1652     }\r
1653 #endif\r
1654 \r
1655     /// <summary>\r
1656     /// Draws a series of rectangles.\r
1657     /// </summary>\r
1658     public void DrawRectangles(XPen pen, XBrush brush, XRect[] rectangles)\r
1659     {\r
1660       if (pen == null && brush == null)\r
1661         throw new ArgumentNullException("pen and brush", PSSR.NeedPenOrBrush);\r
1662       if (rectangles == null)\r
1663         throw new ArgumentNullException("rectangles");\r
1664 \r
1665       int count = rectangles.Length;\r
1666       if (this.drawGraphics)\r
1667       {\r
1668 #if GDI\r
1669         if (this.targetContext == XGraphicTargetContext.GDI)\r
1670         {\r
1671           RectangleF[] rects = new RectangleF[count];\r
1672           for (int idx = 0; idx < count; idx++)\r
1673           {\r
1674             XRect rect = rectangles[idx];\r
1675             rects[idx] = new RectangleF((float)rect.X, (float)rect.Y, (float)rect.Width, (float)rect.Height);\r
1676           }\r
1677           if (brush != null)\r
1678             this.gfx.FillRectangles(brush.RealizeGdiBrush(), rects);\r
1679           if (pen != null)\r
1680             this.gfx.DrawRectangles(pen.RealizeGdiPen(), rects);\r
1681         }\r
1682 #endif\r
1683 #if WPF\r
1684         if (this.targetContext == XGraphicTargetContext.WPF)\r
1685         {\r
1686           System.Windows.Media.Brush wpfBrush = brush != null ? brush.RealizeWpfBrush() : null;\r
1687           System.Windows.Media.Pen wpfPen = pen != null ? pen.RealizeWpfPen() : null;\r
1688           for (int idx = 0; idx < count; idx++)\r
1689           {\r
1690             XRect rect = rectangles[idx];\r
1691             this.dc.DrawRectangle(wpfBrush, wpfPen, new System.Windows.Rect(new System.Windows.Point(rect.x, rect.y), new System.Windows.Size(rect.width, rect.height)));\r
1692           }\r
1693         }\r
1694 #endif\r
1695       }\r
1696 \r
1697       if (this.renderer != null)\r
1698       {\r
1699         for (int idx = 0; idx < count; idx++)\r
1700         {\r
1701           XRect rect = rectangles[idx];\r
1702           this.renderer.DrawRectangle(pen, brush, rect.X, rect.Y, rect.Width, rect.Height);\r
1703         }\r
1704       }\r
1705     }\r
1706 \r
1707     // ----- DrawRoundedRectangle -----------------------------------------------------------------\r
1708 \r
1709     // ----- stroke -----\r
1710 \r
1711 #if GDI\r
1712     /// <summary>\r
1713     /// Draws a rectangles with round corners.\r
1714     /// </summary>\r
1715     public void DrawRoundedRectangle(XPen pen, Rectangle rect, System.Drawing.Size ellipseSize)\r
1716     {\r
1717       DrawRoundedRectangle(pen, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height,\r
1718         (double)ellipseSize.Width, (double)ellipseSize.Height);\r
1719     }\r
1720 #endif\r
1721 \r
1722 #if WPF\r
1723     /// <summary>\r
1724     /// Draws a rectangles with round corners.\r
1725     /// </summary>\r
1726     public void DrawRoundedRectangle(XPen pen, Rect rect, System.Windows.Size ellipseSize)\r
1727     {\r
1728       DrawRoundedRectangle(pen, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height,\r
1729         (double)ellipseSize.Width, (double)ellipseSize.Height);\r
1730     }\r
1731 #endif\r
1732 \r
1733 #if GDI\r
1734     /// <summary>\r
1735     /// Draws a rectangles with round corners.\r
1736     /// </summary>\r
1737     public void DrawRoundedRectangle(XPen pen, RectangleF rect, SizeF ellipseSize)\r
1738     {\r
1739       DrawRoundedRectangle(pen, rect.X, rect.Y, rect.Width, rect.Height, ellipseSize.Width, ellipseSize.Height);\r
1740     }\r
1741 #endif\r
1742 \r
1743     /// <summary>\r
1744     /// Draws a rectangles with round corners.\r
1745     /// </summary>\r
1746     public void DrawRoundedRectangle(XPen pen, XRect rect, XSize ellipseSize)\r
1747     {\r
1748       DrawRoundedRectangle(pen, rect.X, rect.Y, rect.Width, rect.Height, ellipseSize.Width, ellipseSize.Height);\r
1749     }\r
1750 \r
1751     /// <summary>\r
1752     /// Draws a rectangles with round corners.\r
1753     /// </summary>\r
1754     public void DrawRoundedRectangle(XPen pen, int x, int y, int width, int height, int ellipseWidth, int ellipseHeight)\r
1755     {\r
1756       DrawRoundedRectangle(pen, (double)x, (double)y, (double)width, (double)height, (double)ellipseWidth, (double)ellipseHeight);\r
1757     }\r
1758 \r
1759     /// <summary>\r
1760     /// Draws a rectangles with round corners.\r
1761     /// </summary>\r
1762     public void DrawRoundedRectangle(XPen pen, double x, double y, double width, double height, double ellipseWidth, double ellipseHeight)\r
1763     {\r
1764       if (pen == null)\r
1765         throw new ArgumentNullException("pen");\r
1766 \r
1767       DrawRoundedRectangle(pen, null, x, y, width, height, ellipseWidth, ellipseHeight);\r
1768     }\r
1769 \r
1770     // ----- fill -----\r
1771 \r
1772 #if GDI\r
1773     /// <summary>\r
1774     /// Draws a rectangles with round corners.\r
1775     /// </summary>\r
1776     public void DrawRoundedRectangle(XBrush brush, Rectangle rect, System.Drawing.Size ellipseSize)\r
1777     {\r
1778       DrawRoundedRectangle(brush, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height,\r
1779         (double)ellipseSize.Width, (double)ellipseSize.Height);\r
1780     }\r
1781 #endif\r
1782 \r
1783 #if WPF\r
1784     /// <summary>\r
1785     /// Draws a rectangles with round corners.\r
1786     /// </summary>\r
1787     public void DrawRoundedRectangle(XBrush brush, Rect rect, System.Windows.Size ellipseSize)\r
1788     {\r
1789       DrawRoundedRectangle(brush, rect.X, rect.Y, rect.Width, rect.Height, ellipseSize.Width, ellipseSize.Height);\r
1790     }\r
1791 #endif\r
1792 \r
1793 #if GDI\r
1794     /// <summary>\r
1795     /// Draws a rectangles with round corners.\r
1796     /// </summary>\r
1797     public void DrawRoundedRectangle(XBrush brush, RectangleF rect, SizeF ellipseSize)\r
1798     {\r
1799       DrawRoundedRectangle(brush, rect.X, rect.Y, rect.Width, rect.Height, ellipseSize.Width, ellipseSize.Height);\r
1800     }\r
1801 #endif\r
1802 \r
1803     /// <summary>\r
1804     /// Draws a rectangles with round corners.\r
1805     /// </summary>\r
1806     public void DrawRoundedRectangle(XBrush brush, XRect rect, XSize ellipseSize)\r
1807     {\r
1808       DrawRoundedRectangle(brush, rect.X, rect.Y, rect.Width, rect.Height, ellipseSize.Width, ellipseSize.Height);\r
1809     }\r
1810 \r
1811     /// <summary>\r
1812     /// Draws a rectangles with round corners.\r
1813     /// </summary>\r
1814     public void DrawRoundedRectangle(XBrush brush, int x, int y, int width, int height, int ellipseWidth, int ellipseHeight)\r
1815     {\r
1816       DrawRoundedRectangle(brush, (double)x, (double)y, (double)width, (double)height, (double)ellipseWidth, (double)ellipseHeight);\r
1817     }\r
1818 \r
1819     /// <summary>\r
1820     /// Draws a rectangles with round corners.\r
1821     /// </summary>\r
1822     public void DrawRoundedRectangle(XBrush brush, double x, double y, double width, double height, double ellipseWidth, double ellipseHeight)\r
1823     {\r
1824       if (brush == null)\r
1825         throw new ArgumentNullException("brush");\r
1826 \r
1827       DrawRoundedRectangle(null, brush, x, y, width, height, ellipseWidth, ellipseHeight);\r
1828     }\r
1829 \r
1830     // ----- stroke and fill -----\r
1831 \r
1832 #if GDI\r
1833     /// <summary>\r
1834     /// Draws a rectangles with round corners.\r
1835     /// </summary>\r
1836     public void DrawRoundedRectangle(XPen pen, XBrush brush, Rectangle rect, System.Drawing.Size ellipseSize)\r
1837     {\r
1838       DrawRoundedRectangle(pen, brush, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height,\r
1839         (double)ellipseSize.Width, (double)ellipseSize.Height);\r
1840     }\r
1841 #endif\r
1842 \r
1843 #if WPF\r
1844     /// <summary>\r
1845     /// Draws a rectangles with round corners.\r
1846     /// </summary>\r
1847     public void DrawRoundedRectangle(XPen pen, XBrush brush, Rect rect, System.Windows.Size ellipseSize)\r
1848     {\r
1849       DrawRoundedRectangle(pen, brush, rect.X, rect.Y, rect.Width, rect.Height, ellipseSize.Width, ellipseSize.Height);\r
1850     }\r
1851 #endif\r
1852 \r
1853 #if GDI\r
1854     /// <summary>\r
1855     /// Draws a rectangles with round corners.\r
1856     /// </summary>\r
1857     public void DrawRoundedRectangle(XPen pen, XBrush brush, RectangleF rect, SizeF ellipseSize)\r
1858     {\r
1859       DrawRoundedRectangle(pen, brush, rect.X, rect.Y, rect.Width, rect.Height, ellipseSize.Width, ellipseSize.Height);\r
1860     }\r
1861 #endif\r
1862 \r
1863     /// <summary>\r
1864     /// Draws a rectangles with round corners.\r
1865     /// </summary>\r
1866     public void DrawRoundedRectangle(XPen pen, XBrush brush, XRect rect, XSize ellipseSize)\r
1867     {\r
1868       DrawRoundedRectangle(pen, brush, rect.X, rect.Y, rect.Width, rect.Height, ellipseSize.Width, ellipseSize.Height);\r
1869     }\r
1870 \r
1871     /// <summary>\r
1872     /// Draws a rectangles with round corners.\r
1873     /// </summary>\r
1874     public void DrawRoundedRectangle(XPen pen, XBrush brush, int x, int y, int width, int height, int ellipseWidth, int ellipseHeight)\r
1875     {\r
1876       DrawRoundedRectangle(pen, brush, (double)x, (double)y, (double)width, (double)height, (double)ellipseWidth, (double)ellipseHeight);\r
1877     }\r
1878 \r
1879     /// <summary>\r
1880     /// Draws a rectangles with round corners.\r
1881     /// </summary>\r
1882     public void DrawRoundedRectangle(XPen pen, XBrush brush, double x, double y, double width, double height,\r
1883       double ellipseWidth, double ellipseHeight)\r
1884     {\r
1885       if (pen == null && brush == null)\r
1886         throw new ArgumentNullException("pen and brush", PSSR.NeedPenOrBrush);\r
1887 \r
1888       if (this.drawGraphics)\r
1889       {\r
1890 #if GDI\r
1891         if (this.targetContext == XGraphicTargetContext.GDI)\r
1892         {\r
1893           XGraphicsPath path = new XGraphicsPath();\r
1894           path.AddRoundedRectangle(x, y, width, height, ellipseWidth, ellipseHeight);\r
1895           DrawPath(pen, brush, path);\r
1896         }\r
1897 #endif\r
1898 #if WPF\r
1899         if (this.targetContext == XGraphicTargetContext.WPF)\r
1900         {\r
1901 #if !SILVERLIGHT\r
1902           this.dc.DrawRoundedRectangle(\r
1903             brush != null ? brush.RealizeWpfBrush() : null,\r
1904             pen != null ? pen.RealizeWpfPen() : null,\r
1905             new Rect(x, y, width, height), ellipseWidth / 2, ellipseHeight / 2);\r
1906 #else\r
1907           // AGHACK\r
1908 #endif\r
1909         }\r
1910 #endif\r
1911       }\r
1912 \r
1913       if (this.renderer != null)\r
1914         this.renderer.DrawRoundedRectangle(pen, brush, x, y, width, height, ellipseWidth, ellipseHeight);\r
1915     }\r
1916 \r
1917     // ----- DrawEllipse --------------------------------------------------------------------------\r
1918 \r
1919     // ----- stroke -----\r
1920 \r
1921 #if GDI\r
1922     /// <summary>\r
1923     /// Draws an ellipse defined by a bounding rectangle.\r
1924     /// </summary>\r
1925     public void DrawEllipse(XPen pen, Rectangle rect)\r
1926     {\r
1927       DrawEllipse(pen, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height);\r
1928     }\r
1929 #endif\r
1930 \r
1931 #if GDI\r
1932     /// <summary>\r
1933     /// Draws an ellipse defined by a bounding rectangle.\r
1934     /// </summary>\r
1935     public void DrawEllipse(XPen pen, RectangleF rect)\r
1936     {\r
1937       DrawEllipse(pen, rect.X, rect.Y, rect.Width, rect.Height);\r
1938     }\r
1939 #endif\r
1940 \r
1941     /// <summary>\r
1942     /// Draws an ellipse defined by a bounding rectangle.\r
1943     /// </summary>\r
1944     public void DrawEllipse(XPen pen, XRect rect)\r
1945     {\r
1946       DrawEllipse(pen, rect.X, rect.Y, rect.Width, rect.Height);\r
1947     }\r
1948 \r
1949     /// <summary>\r
1950     /// Draws an ellipse defined by a bounding rectangle.\r
1951     /// </summary>\r
1952     public void DrawEllipse(XPen pen, int x, int y, int width, int height)\r
1953     {\r
1954       DrawEllipse(pen, (double)x, (double)y, (double)width, (double)height);\r
1955     }\r
1956 \r
1957     /// <summary>\r
1958     /// Draws an ellipse defined by a bounding rectangle.\r
1959     /// </summary>\r
1960     public void DrawEllipse(XPen pen, double x, double y, double width, double height)\r
1961     {\r
1962       if (pen == null)\r
1963         throw new ArgumentNullException("pen");\r
1964 \r
1965       // No DrawArc defined?\r
1966       if (this.drawGraphics)\r
1967       {\r
1968 #if GDI\r
1969         if (this.targetContext == XGraphicTargetContext.GDI)\r
1970           this.gfx.DrawArc(pen.RealizeGdiPen(), (float)x, (float)y, (float)width, (float)height, 0, 360);\r
1971 #endif\r
1972 #if WPF\r
1973         if (this.targetContext == XGraphicTargetContext.WPF)\r
1974         {\r
1975 #if !SILVERLIGHT\r
1976           double radiusX = width / 2;\r
1977           double radiusY = height / 2;\r
1978           this.dc.DrawEllipse(null, pen.RealizeWpfPen(), new System.Windows.Point(x + radiusX, y + radiusY), radiusX, radiusY);\r
1979 #else\r
1980           // AGHACK\r
1981 #endif\r
1982         }\r
1983 #endif\r
1984       }\r
1985 \r
1986       if (this.renderer != null)\r
1987         this.renderer.DrawEllipse(pen, null, x, y, width, height);\r
1988     }\r
1989 \r
1990     // ----- fill -----\r
1991 \r
1992 #if GDI\r
1993     /// <summary>\r
1994     /// Draws an ellipse defined by a bounding rectangle.\r
1995     /// </summary>\r
1996     public void DrawEllipse(XBrush brush, Rectangle rect)\r
1997     {\r
1998       DrawEllipse(brush, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height);\r
1999     }\r
2000 #endif\r
2001 \r
2002 #if GDI\r
2003     /// <summary>\r
2004     /// Draws an ellipse defined by a bounding rectangle.\r
2005     /// </summary>\r
2006     public void DrawEllipse(XBrush brush, RectangleF rect)\r
2007     {\r
2008       DrawEllipse(brush, rect.X, rect.Y, rect.Width, rect.Height);\r
2009     }\r
2010 #endif\r
2011 \r
2012     /// <summary>\r
2013     /// Draws an ellipse defined by a bounding rectangle.\r
2014     /// </summary>\r
2015     public void DrawEllipse(XBrush brush, XRect rect)\r
2016     {\r
2017       DrawEllipse(brush, rect.X, rect.Y, rect.Width, rect.Height);\r
2018     }\r
2019 \r
2020     /// <summary>\r
2021     /// Draws an ellipse defined by a bounding rectangle.\r
2022     /// </summary>\r
2023     public void DrawEllipse(XBrush brush, int x, int y, int width, int height)\r
2024     {\r
2025       DrawEllipse(brush, (double)x, (double)y, (double)width, (double)height);\r
2026     }\r
2027 \r
2028     /// <summary>\r
2029     /// Draws an ellipse defined by a bounding rectangle.\r
2030     /// </summary>\r
2031     public void DrawEllipse(XBrush brush, double x, double y, double width, double height)\r
2032     {\r
2033       if (brush == null)\r
2034         throw new ArgumentNullException("brush");\r
2035 \r
2036       if (this.drawGraphics)\r
2037       {\r
2038 #if GDI\r
2039         if (this.targetContext == XGraphicTargetContext.GDI)\r
2040           this.gfx.FillEllipse(brush.RealizeGdiBrush(), (float)x, (float)y, (float)width, (float)height);\r
2041 #endif\r
2042 #if WPF\r
2043         if (this.targetContext == XGraphicTargetContext.WPF)\r
2044         {\r
2045 #if !SILVERLIGHT\r
2046           double radiusX = width / 2;\r
2047           double radiusY = height / 2;\r
2048           this.dc.DrawEllipse(brush.RealizeWpfBrush(), null, new System.Windows.Point(x + radiusX, y + radiusY), radiusX, radiusY);\r
2049 #else\r
2050           // AGHACK\r
2051 #endif\r
2052         }\r
2053 #endif\r
2054       }\r
2055 \r
2056       if (this.renderer != null)\r
2057         this.renderer.DrawEllipse(null, brush, x, y, width, height);\r
2058     }\r
2059 \r
2060     // ----- stroke and fill -----\r
2061 \r
2062 #if GDI\r
2063     /// <summary>\r
2064     /// Draws an ellipse defined by a bounding rectangle.\r
2065     /// </summary>\r
2066     public void DrawEllipse(XPen pen, XBrush brush, Rectangle rect)\r
2067     {\r
2068       DrawEllipse(pen, brush, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height);\r
2069     }\r
2070 #endif\r
2071 \r
2072 #if GDI\r
2073     /// <summary>\r
2074     /// Draws an ellipse defined by a bounding rectangle.\r
2075     /// </summary>\r
2076     public void DrawEllipse(XPen pen, XBrush brush, RectangleF rect)\r
2077     {\r
2078       DrawEllipse(pen, brush, rect.X, rect.Y, rect.Width, rect.Height);\r
2079     }\r
2080 #endif\r
2081 \r
2082     /// <summary>\r
2083     /// Draws an ellipse defined by a bounding rectangle.\r
2084     /// </summary>\r
2085     public void DrawEllipse(XPen pen, XBrush brush, XRect rect)\r
2086     {\r
2087       DrawEllipse(pen, brush, rect.X, rect.Y, rect.Width, rect.Height);\r
2088     }\r
2089 \r
2090     /// <summary>\r
2091     /// Draws an ellipse defined by a bounding rectangle.\r
2092     /// </summary>\r
2093     public void DrawEllipse(XPen pen, XBrush brush, int x, int y, int width, int height)\r
2094     {\r
2095       DrawEllipse(pen, brush, (double)x, (double)y, (double)width, (double)height);\r
2096     }\r
2097 \r
2098     /// <summary>\r
2099     /// Draws an ellipse defined by a bounding rectangle.\r
2100     /// </summary>\r
2101     public void DrawEllipse(XPen pen, XBrush brush, double x, double y, double width, double height)\r
2102     {\r
2103       if (pen == null && brush == null)\r
2104         throw new ArgumentNullException("pen and brush", PSSR.NeedPenOrBrush);\r
2105 \r
2106       if (this.drawGraphics)\r
2107       {\r
2108 #if GDI\r
2109         if (this.targetContext == XGraphicTargetContext.GDI)\r
2110         {\r
2111           this.gfx.FillEllipse(brush.RealizeGdiBrush(), (float)x, (float)y, (float)width, (float)height);\r
2112           this.gfx.DrawArc(pen.RealizeGdiPen(), (float)x, (float)y, (float)width, (float)height, 0, 360);\r
2113         }\r
2114 #endif\r
2115 #if WPF\r
2116         if (this.targetContext == XGraphicTargetContext.WPF)\r
2117         {\r
2118 #if !SILVERLIGHT\r
2119           double radiusX = width / 2;\r
2120           double radiusY = height / 2;\r
2121           this.dc.DrawEllipse(brush.RealizeWpfBrush(), pen.RealizeWpfPen(), new System.Windows.Point(x + radiusX, y + radiusY), radiusX, radiusY);\r
2122 #else\r
2123           // AGHACK\r
2124 #endif\r
2125         }\r
2126 #endif\r
2127       }\r
2128 \r
2129       if (this.renderer != null)\r
2130         this.renderer.DrawEllipse(pen, brush, x, y, width, height);\r
2131     }\r
2132 \r
2133     // ----- DrawPolygon --------------------------------------------------------------------------\r
2134 \r
2135     // ----- stroke -----\r
2136 \r
2137 #if GDI\r
2138     /// <summary>\r
2139     /// Draws a polygon defined by an array of points.\r
2140     /// </summary>\r
2141     public void DrawPolygon(XPen pen, System.Drawing.Point[] points)\r
2142     {\r
2143       DrawPolygon(pen, MakeXPointArray(points));\r
2144     }\r
2145 #endif\r
2146 \r
2147 #if WPF\r
2148     /// <summary>\r
2149     /// Draws a polygon defined by an array of points.\r
2150     /// </summary>\r
2151     public void DrawPolygon(XPen pen, System.Windows.Point[] points)\r
2152     {\r
2153       DrawPolygon(pen, MakeXPointArray(points));\r
2154     }\r
2155 #endif\r
2156 \r
2157 #if GDI\r
2158     /// <summary>\r
2159     /// Draws a polygon defined by an array of points.\r
2160     /// </summary>\r
2161     public void DrawPolygon(XPen pen, PointF[] points)\r
2162     {\r
2163       DrawPolygon(pen, MakeXPointArray(points));\r
2164     }\r
2165 #endif\r
2166 \r
2167     /// <summary>\r
2168     /// Draws a polygon defined by an array of points.\r
2169     /// </summary>\r
2170     public void DrawPolygon(XPen pen, XPoint[] points)\r
2171     {\r
2172       if (pen == null)\r
2173         throw new ArgumentNullException("pen");\r
2174       if (points == null)\r
2175         throw new ArgumentNullException("points");\r
2176       if (points.Length < 2)\r
2177         throw new ArgumentException("points", PSSR.PointArrayAtLeast(2));\r
2178 \r
2179       if (this.drawGraphics)\r
2180       {\r
2181 #if GDI\r
2182         if (this.targetContext == XGraphicTargetContext.GDI)\r
2183           this.gfx.DrawPolygon(pen.RealizeGdiPen(), MakePointFArray(points));\r
2184 #endif\r
2185 #if WPF\r
2186         if (this.targetContext == XGraphicTargetContext.WPF)\r
2187         {\r
2188           this.dc.DrawGeometry(null, pen.RealizeWpfPen(), GeometryHelper.CreatePolygonGeometry(MakePointArray(points), XFillMode.Alternate, true));\r
2189         }\r
2190 #endif\r
2191       }\r
2192 \r
2193       if (this.renderer != null)\r
2194         this.renderer.DrawPolygon(pen, null, points, XFillMode.Alternate);  // XFillMode is ignored\r
2195     }\r
2196 \r
2197     // ----- fill -----\r
2198 \r
2199 #if GDI\r
2200     /// <summary>\r
2201     /// Draws a polygon defined by an array of points.\r
2202     /// </summary>\r
2203     public void DrawPolygon(XBrush brush, System.Drawing.Point[] points, XFillMode fillmode)\r
2204     {\r
2205       DrawPolygon(brush, MakeXPointArray(points), fillmode);\r
2206     }\r
2207 #endif\r
2208 \r
2209 #if WPF\r
2210     /// <summary>\r
2211     /// Draws a polygon defined by an array of points.\r
2212     /// </summary>\r
2213     public void DrawPolygon(XBrush brush, System.Windows.Point[] points, XFillMode fillmode)\r
2214     {\r
2215       DrawPolygon(brush, MakeXPointArray(points), fillmode);\r
2216     }\r
2217 #endif\r
2218 \r
2219 #if GDI\r
2220     /// <summary>\r
2221     /// Draws a polygon defined by an array of points.\r
2222     /// </summary>\r
2223     public void DrawPolygon(XBrush brush, PointF[] points, XFillMode fillmode)\r
2224     {\r
2225       DrawPolygon(brush, MakeXPointArray(points), fillmode);\r
2226     }\r
2227 #endif\r
2228 \r
2229     /// <summary>\r
2230     /// Draws a polygon defined by an array of points.\r
2231     /// </summary>\r
2232     public void DrawPolygon(XBrush brush, XPoint[] points, XFillMode fillmode)\r
2233     {\r
2234       if (brush == null)\r
2235         throw new ArgumentNullException("brush");\r
2236       if (points == null)\r
2237         throw new ArgumentNullException("points");\r
2238       if (points.Length < 2)\r
2239         throw new ArgumentException("points", PSSR.PointArrayAtLeast(2));\r
2240 \r
2241       if (this.drawGraphics)\r
2242       {\r
2243 #if GDI\r
2244         if (this.targetContext == XGraphicTargetContext.GDI)\r
2245           this.gfx.FillPolygon(brush.RealizeGdiBrush(), MakePointFArray(points), (FillMode)fillmode);\r
2246 #endif\r
2247 #if WPF\r
2248         if (this.targetContext == XGraphicTargetContext.WPF)\r
2249         {\r
2250           this.dc.DrawGeometry(brush.RealizeWpfBrush(), null, GeometryHelper.CreatePolygonGeometry(MakePointArray(points), fillmode, true));\r
2251         }\r
2252 #endif\r
2253       }\r
2254 \r
2255       if (this.renderer != null)\r
2256         this.renderer.DrawPolygon(null, brush, points, fillmode);\r
2257     }\r
2258 \r
2259     // ----- stroke and fill -----\r
2260 \r
2261 #if GDI\r
2262     /// <summary>\r
2263     /// Draws a polygon defined by an array of points.\r
2264     /// </summary>\r
2265     public void DrawPolygon(XPen pen, XBrush brush, System.Drawing.Point[] points, XFillMode fillmode)\r
2266     {\r
2267       DrawPolygon(pen, brush, MakeXPointArray(points), fillmode);\r
2268     }\r
2269 #endif\r
2270 \r
2271 #if WPF\r
2272     /// <summary>\r
2273     /// Draws a polygon defined by an array of points.\r
2274     /// </summary>\r
2275     public void DrawPolygon(XPen pen, XBrush brush, System.Windows.Point[] points, XFillMode fillmode)\r
2276     {\r
2277       DrawPolygon(pen, brush, MakeXPointArray(points), fillmode);\r
2278     }\r
2279 #endif\r
2280 \r
2281 #if GDI\r
2282     /// <summary>\r
2283     /// Draws a polygon defined by an array of points.\r
2284     /// </summary>\r
2285     public void DrawPolygon(XPen pen, XBrush brush, PointF[] points, XFillMode fillmode)\r
2286     {\r
2287       DrawPolygon(pen, brush, MakeXPointArray(points), fillmode);\r
2288     }\r
2289 #endif\r
2290 \r
2291     /// <summary>\r
2292     /// Draws a polygon defined by an array of points.\r
2293     /// </summary>\r
2294     public void DrawPolygon(XPen pen, XBrush brush, XPoint[] points, XFillMode fillmode)\r
2295     {\r
2296       if (pen == null && brush == null)\r
2297         throw new ArgumentNullException("pen and brush", PSSR.NeedPenOrBrush);\r
2298       if (points == null)\r
2299         throw new ArgumentNullException("points");\r
2300       if (points.Length < 2)\r
2301         throw new ArgumentException("points", PSSR.PointArrayAtLeast(2));\r
2302 \r
2303       if (this.drawGraphics)\r
2304       {\r
2305 #if GDI\r
2306         if (this.targetContext == XGraphicTargetContext.GDI)\r
2307         {\r
2308           PointF[] pts = MakePointFArray(points);\r
2309           this.gfx.FillPolygon(brush.RealizeGdiBrush(), pts, (FillMode)fillmode);\r
2310           this.gfx.DrawPolygon(pen.RealizeGdiPen(), pts);\r
2311         }\r
2312 #endif\r
2313 #if WPF\r
2314         if (this.targetContext == XGraphicTargetContext.WPF)\r
2315         {\r
2316           System.Windows.Media.Brush wpfBrush = brush != null ? brush.RealizeWpfBrush() : null;\r
2317           System.Windows.Media.Pen wpfPen = brush != null ? pen.RealizeWpfPen() : null;\r
2318           this.dc.DrawGeometry(wpfBrush, wpfPen, GeometryHelper.CreatePolygonGeometry(MakePointArray(points), fillmode, true));\r
2319         }\r
2320 #endif\r
2321       }\r
2322 \r
2323       if (this.renderer != null)\r
2324         this.renderer.DrawPolygon(pen, brush, points, fillmode);\r
2325     }\r
2326 \r
2327     // ----- DrawPie ------------------------------------------------------------------------------\r
2328 \r
2329     // ----- stroke -----\r
2330 \r
2331 #if GDI\r
2332     /// <summary>\r
2333     /// Draws a pie defined by an ellipse.\r
2334     /// </summary>\r
2335     public void DrawPie(XPen pen, Rectangle rect, double startAngle, double sweepAngle)\r
2336     {\r
2337       DrawPie(pen, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height, startAngle, sweepAngle);\r
2338     }\r
2339 #endif\r
2340 \r
2341 #if GDI\r
2342     /// <summary>\r
2343     /// Draws a pie defined by an ellipse.\r
2344     /// </summary>\r
2345     public void DrawPie(XPen pen, RectangleF rect, double startAngle, double sweepAngle)\r
2346     {\r
2347       DrawPie(pen, rect.X, rect.Y, rect.Width, rect.Height, startAngle, sweepAngle);\r
2348     }\r
2349 #endif\r
2350 \r
2351     /// <summary>\r
2352     /// Draws a pie defined by an ellipse.\r
2353     /// </summary>\r
2354     public void DrawPie(XPen pen, XRect rect, double startAngle, double sweepAngle)\r
2355     {\r
2356       DrawPie(pen, rect.X, rect.Y, rect.Width, rect.Height, startAngle, sweepAngle);\r
2357     }\r
2358 \r
2359     /// <summary>\r
2360     /// Draws a pie defined by an ellipse.\r
2361     /// </summary>\r
2362     public void DrawPie(XPen pen, int x, int y, int width, int height, int startAngle, int sweepAngle)\r
2363     {\r
2364       DrawPie(pen, (double)x, (double)y, (double)width, (double)height, (double)startAngle, (double)sweepAngle);\r
2365     }\r
2366 \r
2367     /// <summary>\r
2368     /// Draws a pie defined by an ellipse.\r
2369     /// </summary>\r
2370     public void DrawPie(XPen pen, double x, double y, double width, double height, double startAngle, double sweepAngle)\r
2371     {\r
2372       if (pen == null)\r
2373         throw new ArgumentNullException("pen", PSSR.NeedPenOrBrush);\r
2374 \r
2375       if (this.drawGraphics)\r
2376       {\r
2377 #if GDI\r
2378         if (this.targetContext == XGraphicTargetContext.GDI)\r
2379           this.gfx.DrawPie(pen.RealizeGdiPen(), (float)x, (float)y, (float)width, (float)height, (float)startAngle, (float)sweepAngle);\r
2380 #endif\r
2381 #if WPF\r
2382         if (this.targetContext == XGraphicTargetContext.WPF)\r
2383           DrawPie(pen, null, x, y, width, height, startAngle, sweepAngle);\r
2384 #endif\r
2385       }\r
2386 \r
2387       if (this.renderer != null)\r
2388         this.renderer.DrawPie(pen, null, x, y, width, height, startAngle, sweepAngle);\r
2389     }\r
2390 \r
2391     // ----- fill -----\r
2392 \r
2393 #if GDI\r
2394     /// <summary>\r
2395     /// Draws a pie defined by an ellipse.\r
2396     /// </summary>\r
2397     public void DrawPie(XBrush brush, Rectangle rect, double startAngle, double sweepAngle)\r
2398     {\r
2399       DrawPie(brush, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height, startAngle, sweepAngle);\r
2400     }\r
2401 #endif\r
2402 \r
2403 #if GDI\r
2404     /// <summary>\r
2405     /// Draws a pie defined by an ellipse.\r
2406     /// </summary>\r
2407     public void DrawPie(XBrush brush, RectangleF rect, double startAngle, double sweepAngle)\r
2408     {\r
2409       DrawPie(brush, rect.X, rect.Y, rect.Width, rect.Height, startAngle, sweepAngle);\r
2410     }\r
2411 #endif\r
2412 \r
2413     /// <summary>\r
2414     /// Draws a pie defined by an ellipse.\r
2415     /// </summary>\r
2416     public void DrawPie(XBrush brush, XRect rect, double startAngle, double sweepAngle)\r
2417     {\r
2418       DrawPie(brush, rect.X, rect.Y, rect.Width, rect.Height, startAngle, sweepAngle);\r
2419     }\r
2420 \r
2421     /// <summary>\r
2422     /// Draws a pie defined by an ellipse.\r
2423     /// </summary>\r
2424     public void DrawPie(XBrush brush, int x, int y, int width, int height, int startAngle, int sweepAngle)\r
2425     {\r
2426       DrawPie(brush, (double)x, (double)y, (double)width, (double)height, (double)startAngle, (double)sweepAngle);\r
2427     }\r
2428 \r
2429     /// <summary>\r
2430     /// Draws a pie defined by an ellipse.\r
2431     /// </summary>\r
2432     public void DrawPie(XBrush brush, double x, double y, double width, double height, double startAngle, double sweepAngle)\r
2433     {\r
2434       if (brush == null)\r
2435         throw new ArgumentNullException("brush", PSSR.NeedPenOrBrush);\r
2436 \r
2437       if (this.drawGraphics)\r
2438       {\r
2439 #if GDI\r
2440         if (this.targetContext == XGraphicTargetContext.GDI)\r
2441           this.gfx.FillPie(brush.RealizeGdiBrush(), (float)x, (float)y, (float)width, (float)height, (float)startAngle, (float)sweepAngle);\r
2442 #endif\r
2443 #if WPF\r
2444         if (this.targetContext == XGraphicTargetContext.WPF)\r
2445           DrawPie(null, brush, x, y, width, height, startAngle, sweepAngle);\r
2446 #endif\r
2447       }\r
2448 \r
2449       if (this.renderer != null)\r
2450         this.renderer.DrawPie(null, brush, x, y, width, height, startAngle, sweepAngle);\r
2451     }\r
2452 \r
2453     // ----- stroke and fill -----\r
2454 \r
2455 #if GDI\r
2456     /// <summary>\r
2457     /// Draws a pie defined by an ellipse.\r
2458     /// </summary>\r
2459     public void DrawPie(XPen pen, XBrush brush, Rectangle rect, double startAngle, double sweepAngle)\r
2460     {\r
2461       DrawPie(pen, brush, (double)rect.X, (double)rect.Y, (double)rect.Width, (double)rect.Height, startAngle, sweepAngle);\r
2462     }\r
2463 #endif\r
2464 \r
2465 #if GDI\r
2466     /// <summary>\r
2467     /// Draws a pie defined by an ellipse.\r
2468     /// </summary>\r
2469     public void DrawPie(XPen pen, XBrush brush, RectangleF rect, double startAngle, double sweepAngle)\r
2470     {\r
2471       DrawPie(pen, brush, rect.X, rect.Y, rect.Width, rect.Height, startAngle, sweepAngle);\r
2472     }\r
2473 #endif\r
2474 \r
2475     /// <summary>\r
2476     /// Draws a pie defined by an ellipse.\r
2477     /// </summary>\r
2478     public void DrawPie(XPen pen, XBrush brush, XRect rect, double startAngle, double sweepAngle)\r
2479     {\r
2480       DrawPie(pen, brush, rect.X, rect.Y, rect.Width, rect.Height, startAngle, sweepAngle);\r
2481     }\r
2482 \r
2483     /// <summary>\r
2484     /// Draws a pie defined by an ellipse.\r
2485     /// </summary>\r
2486     public void DrawPie(XPen pen, XBrush brush, int x, int y, int width, int height, int startAngle, int sweepAngle)\r
2487     {\r
2488       DrawPie(pen, brush, (double)x, (double)y, (double)width, (double)height, (double)startAngle, (double)sweepAngle);\r
2489     }\r
2490 \r
2491     /// <summary>\r
2492     /// Draws a pie defined by an ellipse.\r
2493     /// </summary>\r
2494     public void DrawPie(XPen pen, XBrush brush, double x, double y, double width, double height, double startAngle, double sweepAngle)\r
2495     {\r
2496       if (pen == null && brush == null)\r
2497         throw new ArgumentNullException("pen", PSSR.NeedPenOrBrush);\r
2498 \r
2499       if (this.drawGraphics)\r
2500       {\r
2501 #if GDI\r
2502         if (this.targetContext == XGraphicTargetContext.GDI)\r
2503         {\r
2504           this.gfx.FillPie(brush.RealizeGdiBrush(), (float)x, (float)y, (float)width, (float)height, (float)startAngle, (float)sweepAngle);\r
2505           this.gfx.DrawPie(pen.RealizeGdiPen(), (float)x, (float)y, (float)width, (float)height, (float)startAngle, (float)sweepAngle);\r
2506         }\r
2507 #endif\r
2508 #if WPF\r
2509         if (this.targetContext == XGraphicTargetContext.WPF)\r
2510         {\r
2511 #if !SILVERLIGHT\r
2512           System.Windows.Media.Brush wpfBrush = brush != null ? brush.RealizeWpfBrush() : null;\r
2513           System.Windows.Media.Pen wpfPen = pen != null ? pen.RealizeWpfPen() : null;\r
2514           System.Windows.Point center = new System.Windows.Point(x + width / 2, y + height / 2);\r
2515           System.Windows.Point startArc;\r
2516           ArcSegment arc = GeometryHelper.CreateArcSegment(x, y, width, height, startAngle, sweepAngle, out startArc);\r
2517           PathFigure figure = new PathFigure();\r
2518           figure.StartPoint = center;\r
2519           figure.Segments.Add(new LineSegment(startArc, true));\r
2520           figure.Segments.Add(arc);\r
2521           figure.IsClosed = true;\r
2522           PathGeometry geo = new PathGeometry();\r
2523           geo.Figures.Add(figure);\r
2524           this.dc.DrawGeometry(wpfBrush, wpfPen, geo);\r
2525 #else\r
2526           // AGHACK\r