Added the source code of OxyPlot as of commit d190d7748a73 (6.5.2013).
1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/External/OxyPlot/GlobalAssemblyInfo.cs Sat Jun 08 16:53:22 2013 +0000
1.3 @@ -0,0 +1,38 @@
1.4 +//-----------------------------------------------------------------------
1.5 +// <copyright file="GlobalAssemblyInfo.cs" company="OxyPlot">
1.6 +// The MIT License (MIT)
1.7 +//
1.8 +// Copyright (c) 2012 Oystein Bjorke
1.9 +//
1.10 +// Permission is hereby granted, free of charge, to any person obtaining a
1.11 +// copy of this software and associated documentation files (the
1.12 +// "Software"), to deal in the Software without restriction, including
1.13 +// without limitation the rights to use, copy, modify, merge, publish,
1.14 +// distribute, sublicense, and/or sell copies of the Software, and to
1.15 +// permit persons to whom the Software is furnished to do so, subject to
1.16 +// the following conditions:
1.17 +//
1.18 +// The above copyright notice and this permission notice shall be included
1.19 +// in all copies or substantial portions of the Software.
1.20 +//
1.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
1.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
1.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
1.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
1.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
1.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
1.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
1.28 +// </copyright>
1.29 +//-----------------------------------------------------------------------
1.30 +
1.31 +using System.Reflection;
1.32 +
1.33 +[assembly: AssemblyConfiguration("")]
1.34 +[assembly: AssemblyProduct("OxyPlot")]
1.35 +[assembly: AssemblyCompany("OxyPlot")]
1.36 +[assembly: AssemblyCopyright("Copyright (C) OxyPlot 2012.")]
1.37 +[assembly: AssemblyTrademark("")]
1.38 +[assembly: AssemblyCulture("")]
1.39 +
1.40 +[assembly: AssemblyVersion("2013.1.1.1")]
1.41 +[assembly: AssemblyFileVersion("2013.1.1.1")]
2.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
2.2 +++ b/External/OxyPlot/OxyPlot.WindowsForms/GraphicsRenderContext.cs Sat Jun 08 16:53:22 2013 +0000
2.3 @@ -0,0 +1,558 @@
2.4 +// --------------------------------------------------------------------------------------------------------------------
2.5 +// <copyright file="GraphicsRenderContext.cs" company="OxyPlot">
2.6 +// The MIT License (MIT)
2.7 +//
2.8 +// Copyright (c) 2012 Oystein Bjorke
2.9 +//
2.10 +// Permission is hereby granted, free of charge, to any person obtaining a
2.11 +// copy of this software and associated documentation files (the
2.12 +// "Software"), to deal in the Software without restriction, including
2.13 +// without limitation the rights to use, copy, modify, merge, publish,
2.14 +// distribute, sublicense, and/or sell copies of the Software, and to
2.15 +// permit persons to whom the Software is furnished to do so, subject to
2.16 +// the following conditions:
2.17 +//
2.18 +// The above copyright notice and this permission notice shall be included
2.19 +// in all copies or substantial portions of the Software.
2.20 +//
2.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
2.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
2.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
2.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
2.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
2.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
2.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
2.28 +// </copyright>
2.29 +// <summary>
2.30 +// The graphics render context.
2.31 +// </summary>
2.32 +// --------------------------------------------------------------------------------------------------------------------
2.33 +namespace OxyPlot.WindowsForms
2.34 +{
2.35 + using System;
2.36 + using System.Collections.Generic;
2.37 + using System.Drawing;
2.38 + using System.Drawing.Drawing2D;
2.39 + using System.Drawing.Imaging;
2.40 + using System.IO;
2.41 + using System.Linq;
2.42 +
2.43 + using OxyPlot;
2.44 +
2.45 + /// <summary>
2.46 + /// The graphics render context.
2.47 + /// </summary>
2.48 + internal class GraphicsRenderContext : RenderContextBase
2.49 + {
2.50 + /// <summary>
2.51 + /// The font size factor.
2.52 + /// </summary>
2.53 + private const float FontsizeFactor = 0.8f;
2.54 +
2.55 + /// <summary>
2.56 + /// The GDI+ drawing surface.
2.57 + /// </summary>
2.58 + private Graphics g;
2.59 +
2.60 + /// <summary>
2.61 + /// Initializes a new instance of the <see cref="GraphicsRenderContext"/> class.
2.62 + /// </summary>
2.63 + public GraphicsRenderContext()
2.64 + {
2.65 + }
2.66 +
2.67 + /// <summary>
2.68 + /// Sets the graphics target.
2.69 + /// </summary>
2.70 + /// <param name="graphics">The graphics surface.</param>
2.71 + public void SetGraphicsTarget(Graphics graphics)
2.72 + {
2.73 + this.g = graphics;
2.74 + }
2.75 +
2.76 + /// <summary>
2.77 + /// Draws the ellipse.
2.78 + /// </summary>
2.79 + /// <param name="rect">The rect.</param>
2.80 + /// <param name="fill">The fill.</param>
2.81 + /// <param name="stroke">The stroke.</param>
2.82 + /// <param name="thickness">The thickness.</param>
2.83 + public override void DrawEllipse(OxyRect rect, OxyColor fill, OxyColor stroke, double thickness)
2.84 + {
2.85 + if (fill != null)
2.86 + {
2.87 + this.g.FillEllipse(
2.88 + this.ToBrush(fill), (float)rect.Left, (float)rect.Top, (float)rect.Width, (float)rect.Height);
2.89 + }
2.90 +
2.91 + if (stroke == null || thickness <= 0)
2.92 + {
2.93 + return;
2.94 + }
2.95 +
2.96 + using (var pen = new Pen(this.ToColor(stroke), (float)thickness))
2.97 + {
2.98 + this.g.SmoothingMode = SmoothingMode.HighQuality;
2.99 + this.g.DrawEllipse(pen, (float)rect.Left, (float)rect.Top, (float)rect.Width, (float)rect.Height);
2.100 + }
2.101 + }
2.102 +
2.103 + /// <summary>
2.104 + /// Draws the line.
2.105 + /// </summary>
2.106 + /// <param name="points">The points.</param>
2.107 + /// <param name="stroke">The stroke.</param>
2.108 + /// <param name="thickness">The thickness.</param>
2.109 + /// <param name="dashArray">The dash array.</param>
2.110 + /// <param name="lineJoin">The line join.</param>
2.111 + /// <param name="aliased">if set to <c>true</c> [aliased].</param>
2.112 + public override void DrawLine(
2.113 + IList<ScreenPoint> points,
2.114 + OxyColor stroke,
2.115 + double thickness,
2.116 + double[] dashArray,
2.117 + OxyPenLineJoin lineJoin,
2.118 + bool aliased)
2.119 + {
2.120 + if (stroke == null || thickness <= 0 || points.Count < 2)
2.121 + {
2.122 + return;
2.123 + }
2.124 +
2.125 + this.g.SmoothingMode = aliased ? SmoothingMode.None : SmoothingMode.HighQuality;
2.126 + using (var pen = new Pen(this.ToColor(stroke), (float)thickness))
2.127 + {
2.128 +
2.129 + if (dashArray != null)
2.130 + {
2.131 + pen.DashPattern = this.ToFloatArray(dashArray);
2.132 + }
2.133 +
2.134 + switch (lineJoin)
2.135 + {
2.136 + case OxyPenLineJoin.Round:
2.137 + pen.LineJoin = LineJoin.Round;
2.138 + break;
2.139 + case OxyPenLineJoin.Bevel:
2.140 + pen.LineJoin = LineJoin.Bevel;
2.141 + break;
2.142 +
2.143 + // The default LineJoin is Miter
2.144 + }
2.145 +
2.146 + this.g.DrawLines(pen, this.ToPoints(points));
2.147 + }
2.148 + }
2.149 +
2.150 + /// <summary>
2.151 + /// Draws the polygon.
2.152 + /// </summary>
2.153 + /// <param name="points">The points.</param>
2.154 + /// <param name="fill">The fill.</param>
2.155 + /// <param name="stroke">The stroke.</param>
2.156 + /// <param name="thickness">The thickness.</param>
2.157 + /// <param name="dashArray">The dash array.</param>
2.158 + /// <param name="lineJoin">The line join.</param>
2.159 + /// <param name="aliased">if set to <c>true</c> [aliased].</param>
2.160 + public override void DrawPolygon(
2.161 + IList<ScreenPoint> points,
2.162 + OxyColor fill,
2.163 + OxyColor stroke,
2.164 + double thickness,
2.165 + double[] dashArray,
2.166 + OxyPenLineJoin lineJoin,
2.167 + bool aliased)
2.168 + {
2.169 + if (points.Count < 2)
2.170 + {
2.171 + return;
2.172 + }
2.173 +
2.174 + this.g.SmoothingMode = aliased ? SmoothingMode.None : SmoothingMode.HighQuality;
2.175 +
2.176 + PointF[] pts = this.ToPoints(points);
2.177 + if (fill != null)
2.178 + {
2.179 + this.g.FillPolygon(this.ToBrush(fill), pts);
2.180 + }
2.181 +
2.182 + if (stroke != null && thickness > 0)
2.183 + {
2.184 + using (var pen = new Pen(this.ToColor(stroke), (float)thickness))
2.185 + {
2.186 +
2.187 + if (dashArray != null)
2.188 + {
2.189 + pen.DashPattern = this.ToFloatArray(dashArray);
2.190 + }
2.191 +
2.192 + switch (lineJoin)
2.193 + {
2.194 + case OxyPenLineJoin.Round:
2.195 + pen.LineJoin = LineJoin.Round;
2.196 + break;
2.197 + case OxyPenLineJoin.Bevel:
2.198 + pen.LineJoin = LineJoin.Bevel;
2.199 + break;
2.200 +
2.201 + // The default LineJoin is Miter
2.202 + }
2.203 +
2.204 + this.g.DrawPolygon(pen, pts);
2.205 + }
2.206 + }
2.207 + }
2.208 +
2.209 + /// <summary>
2.210 + /// The draw rectangle.
2.211 + /// </summary>
2.212 + /// <param name="rect">
2.213 + /// The rect.
2.214 + /// </param>
2.215 + /// <param name="fill">
2.216 + /// The fill.
2.217 + /// </param>
2.218 + /// <param name="stroke">
2.219 + /// The stroke.
2.220 + /// </param>
2.221 + /// <param name="thickness">
2.222 + /// The thickness.
2.223 + /// </param>
2.224 + public override void DrawRectangle(OxyRect rect, OxyColor fill, OxyColor stroke, double thickness)
2.225 + {
2.226 + if (fill != null)
2.227 + {
2.228 + this.g.FillRectangle(
2.229 + this.ToBrush(fill), (float)rect.Left, (float)rect.Top, (float)rect.Width, (float)rect.Height);
2.230 + }
2.231 +
2.232 + if (stroke == null || thickness <= 0)
2.233 + {
2.234 + return;
2.235 + }
2.236 +
2.237 + using (var pen = new Pen(this.ToColor(stroke), (float)thickness))
2.238 + {
2.239 + this.g.DrawRectangle(pen, (float)rect.Left, (float)rect.Top, (float)rect.Width, (float)rect.Height);
2.240 + }
2.241 + }
2.242 +
2.243 + /// <summary>
2.244 + /// The draw text.
2.245 + /// </summary>
2.246 + /// <param name="p">
2.247 + /// The p.
2.248 + /// </param>
2.249 + /// <param name="text">
2.250 + /// The text.
2.251 + /// </param>
2.252 + /// <param name="fill">
2.253 + /// The fill.
2.254 + /// </param>
2.255 + /// <param name="fontFamily">
2.256 + /// The font family.
2.257 + /// </param>
2.258 + /// <param name="fontSize">
2.259 + /// The font size.
2.260 + /// </param>
2.261 + /// <param name="fontWeight">
2.262 + /// The font weight.
2.263 + /// </param>
2.264 + /// <param name="rotate">
2.265 + /// The rotate.
2.266 + /// </param>
2.267 + /// <param name="halign">
2.268 + /// The halign.
2.269 + /// </param>
2.270 + /// <param name="valign">
2.271 + /// The valign.
2.272 + /// </param>
2.273 + /// <param name="maxSize">
2.274 + /// The maximum size of the text.
2.275 + /// </param>
2.276 + public override void DrawText(
2.277 + ScreenPoint p,
2.278 + string text,
2.279 + OxyColor fill,
2.280 + string fontFamily,
2.281 + double fontSize,
2.282 + double fontWeight,
2.283 + double rotate,
2.284 + HorizontalAlignment halign,
2.285 + VerticalAlignment valign,
2.286 + OxySize? maxSize)
2.287 + {
2.288 + var fs = FontStyle.Regular;
2.289 + if (fontWeight >= 700)
2.290 + {
2.291 + fs = FontStyle.Bold;
2.292 + }
2.293 +
2.294 + using (var font = new Font(fontFamily, (float)fontSize * FontsizeFactor, fs))
2.295 + {
2.296 + using (var sf = new StringFormat { Alignment = StringAlignment.Near })
2.297 + {
2.298 + var size = this.g.MeasureString(text, font);
2.299 + if (maxSize != null)
2.300 + {
2.301 + if (size.Width > maxSize.Value.Width)
2.302 + {
2.303 + size.Width = (float)maxSize.Value.Width;
2.304 + }
2.305 +
2.306 + if (size.Height > maxSize.Value.Height)
2.307 + {
2.308 + size.Height = (float)maxSize.Value.Height;
2.309 + }
2.310 + }
2.311 +
2.312 + float dx = 0;
2.313 + if (halign == HorizontalAlignment.Center)
2.314 + {
2.315 + dx = -size.Width / 2;
2.316 + }
2.317 +
2.318 + if (halign == HorizontalAlignment.Right)
2.319 + {
2.320 + dx = -size.Width;
2.321 + }
2.322 +
2.323 + float dy = 0;
2.324 + sf.LineAlignment = StringAlignment.Near;
2.325 + if (valign == VerticalAlignment.Middle)
2.326 + {
2.327 + dy = -size.Height / 2;
2.328 + }
2.329 +
2.330 + if (valign == VerticalAlignment.Bottom)
2.331 + {
2.332 + dy = -size.Height;
2.333 + }
2.334 +
2.335 + this.g.TranslateTransform((float)p.X, (float)p.Y);
2.336 + if (Math.Abs(rotate) > double.Epsilon)
2.337 + {
2.338 + this.g.RotateTransform((float)rotate);
2.339 + }
2.340 +
2.341 + this.g.TranslateTransform(dx, dy);
2.342 +
2.343 + var layoutRectangle = new RectangleF(0, 0, size.Width, size.Height);
2.344 + this.g.DrawString(text, font, this.ToBrush(fill), layoutRectangle, sf);
2.345 +
2.346 + this.g.ResetTransform();
2.347 + }
2.348 + }
2.349 + }
2.350 +
2.351 + /// <summary>
2.352 + /// The measure text.
2.353 + /// </summary>
2.354 + /// <param name="text">The text.</param>
2.355 + /// <param name="fontFamily">The font family.</param>
2.356 + /// <param name="fontSize">The font size.</param>
2.357 + /// <param name="fontWeight">The font weight.</param>
2.358 + /// <returns>The size of the text.</returns>
2.359 + public override OxySize MeasureText(string text, string fontFamily, double fontSize, double fontWeight)
2.360 + {
2.361 + if (text == null)
2.362 + {
2.363 + return OxySize.Empty;
2.364 + }
2.365 +
2.366 + var fs = FontStyle.Regular;
2.367 + if (fontWeight >= 700)
2.368 + {
2.369 + fs = FontStyle.Bold;
2.370 + }
2.371 +
2.372 + using (var font = new Font(fontFamily, (float)fontSize * FontsizeFactor, fs))
2.373 + {
2.374 + var size = this.g.MeasureString(text, font);
2.375 + return new OxySize(size.Width, size.Height);
2.376 + }
2.377 + }
2.378 +
2.379 + /// <summary>
2.380 + /// Converts a fill color to a System.Drawing.Brush.
2.381 + /// </summary>
2.382 + /// <param name="fill">
2.383 + /// The fill color.
2.384 + /// </param>
2.385 + /// <returns>
2.386 + /// The brush.
2.387 + /// </returns>
2.388 + private Brush ToBrush(OxyColor fill)
2.389 + {
2.390 + if (fill != null)
2.391 + {
2.392 + return new SolidBrush(this.ToColor(fill));
2.393 + }
2.394 +
2.395 + return null;
2.396 + }
2.397 +
2.398 + /// <summary>
2.399 + /// Converts a color to a System.Drawing.Color.
2.400 + /// </summary>
2.401 + /// <param name="c">
2.402 + /// The color.
2.403 + /// </param>
2.404 + /// <returns>
2.405 + /// The System.Drawing.Color.
2.406 + /// </returns>
2.407 + private Color ToColor(OxyColor c)
2.408 + {
2.409 + return Color.FromArgb(c.A, c.R, c.G, c.B);
2.410 + }
2.411 +
2.412 + /// <summary>
2.413 + /// Converts a double array to a float array.
2.414 + /// </summary>
2.415 + /// <param name="a">
2.416 + /// The a.
2.417 + /// </param>
2.418 + /// <returns>
2.419 + /// The float array.
2.420 + /// </returns>
2.421 + private float[] ToFloatArray(double[] a)
2.422 + {
2.423 + if (a == null)
2.424 + {
2.425 + return null;
2.426 + }
2.427 +
2.428 + var r = new float[a.Length];
2.429 + for (int i = 0; i < a.Length; i++)
2.430 + {
2.431 + r[i] = (float)a[i];
2.432 + }
2.433 +
2.434 + return r;
2.435 + }
2.436 +
2.437 + /// <summary>
2.438 + /// Converts a list of point to an array of PointF.
2.439 + /// </summary>
2.440 + /// <param name="points">
2.441 + /// The points.
2.442 + /// </param>
2.443 + /// <returns>
2.444 + /// An array of points.
2.445 + /// </returns>
2.446 + private PointF[] ToPoints(IList<ScreenPoint> points)
2.447 + {
2.448 + if (points == null)
2.449 + {
2.450 + return null;
2.451 + }
2.452 +
2.453 + var r = new PointF[points.Count()];
2.454 + int i = 0;
2.455 + foreach (ScreenPoint p in points)
2.456 + {
2.457 + r[i++] = new PointF((float)p.X, (float)p.Y);
2.458 + }
2.459 +
2.460 + return r;
2.461 + }
2.462 +
2.463 + public override void CleanUp()
2.464 + {
2.465 + var imagesToRelease = imageCache.Keys.Where(i => !imagesInUse.Contains(i));
2.466 + foreach (var i in imagesToRelease)
2.467 + {
2.468 + var image = this.GetImage(i);
2.469 + image.Dispose();
2.470 + imageCache.Remove(i);
2.471 + }
2.472 +
2.473 + imagesInUse.Clear();
2.474 + }
2.475 +
2.476 + public override OxyImageInfo GetImageInfo(OxyImage source)
2.477 + {
2.478 + var image = this.GetImage(source);
2.479 + return image == null ? null : new OxyImageInfo { Width = (uint)image.Width, Height = (uint)image.Height, DpiX = image.HorizontalResolution, DpiY = image.VerticalResolution };
2.480 + }
2.481 +
2.482 + public override void DrawImage(OxyImage source, uint srcX, uint srcY, uint srcWidth, uint srcHeight, double x, double y, double w, double h, double opacity, bool interpolate)
2.483 + {
2.484 + var image = this.GetImage(source);
2.485 + if (image != null)
2.486 + {
2.487 + ImageAttributes ia = null;
2.488 + if (opacity < 1)
2.489 + {
2.490 + var cm = new ColorMatrix
2.491 + {
2.492 + Matrix00 = 1f,
2.493 + Matrix11 = 1f,
2.494 + Matrix22 = 1f,
2.495 + Matrix33 = 1f,
2.496 + Matrix44 = (float)opacity
2.497 + };
2.498 +
2.499 + ia = new ImageAttributes();
2.500 + ia.SetColorMatrix(cm, ColorMatrixFlag.Default, ColorAdjustType.Bitmap);
2.501 + }
2.502 +
2.503 + g.InterpolationMode = interpolate ? InterpolationMode.HighQualityBicubic : InterpolationMode.NearestNeighbor;
2.504 + int sx = (int)Math.Round(x);
2.505 + int sy = (int)Math.Round(y);
2.506 + int sw = (int)Math.Round(x + w) - sx;
2.507 + int sh = (int)Math.Round(y + h) - sy;
2.508 + g.DrawImage(image, new Rectangle(sx, sy, sw, sh), srcX, srcY, srcWidth, srcHeight, GraphicsUnit.Pixel, ia);
2.509 + }
2.510 + }
2.511 +
2.512 + private HashSet<OxyImage> imagesInUse = new HashSet<OxyImage>();
2.513 +
2.514 + private Dictionary<OxyImage, Image> imageCache = new Dictionary<OxyImage, Image>();
2.515 +
2.516 +
2.517 + private Image GetImage(OxyImage source)
2.518 + {
2.519 + if (source == null)
2.520 + {
2.521 + return null;
2.522 + }
2.523 +
2.524 + if (!this.imagesInUse.Contains(source))
2.525 + {
2.526 + this.imagesInUse.Add(source);
2.527 + }
2.528 +
2.529 + Image src;
2.530 + if (this.imageCache.TryGetValue(source, out src))
2.531 + {
2.532 + return src;
2.533 + }
2.534 +
2.535 + if (source != null)
2.536 + {
2.537 + Image btm;
2.538 + using (var ms = new MemoryStream(source.GetData()))
2.539 + {
2.540 + btm = Image.FromStream(ms);
2.541 + }
2.542 +
2.543 + this.imageCache.Add(source, btm);
2.544 + return btm;
2.545 + }
2.546 +
2.547 + return null;
2.548 + }
2.549 +
2.550 + public override bool SetClip(OxyRect rect)
2.551 + {
2.552 + this.g.SetClip(rect.ToRect(false));
2.553 + return true;
2.554 + }
2.555 +
2.556 + public override void ResetClip()
2.557 + {
2.558 + this.g.ResetClip();
2.559 + }
2.560 + }
2.561 +}
2.562 \ No newline at end of file
3.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
3.2 +++ b/External/OxyPlot/OxyPlot.WindowsForms/Helpers/ConverterExtensions.cs Sat Jun 08 16:53:22 2013 +0000
3.3 @@ -0,0 +1,251 @@
3.4 +// --------------------------------------------------------------------------------------------------------------------
3.5 +// <copyright file="ConverterExtensions.cs" company="OxyPlot">
3.6 +// The MIT License (MIT)
3.7 +//
3.8 +// Copyright (c) 2012 Oystein Bjorke
3.9 +//
3.10 +// Permission is hereby granted, free of charge, to any person obtaining a
3.11 +// copy of this software and associated documentation files (the
3.12 +// "Software"), to deal in the Software without restriction, including
3.13 +// without limitation the rights to use, copy, modify, merge, publish,
3.14 +// distribute, sublicense, and/or sell copies of the Software, and to
3.15 +// permit persons to whom the Software is furnished to do so, subject to
3.16 +// the following conditions:
3.17 +//
3.18 +// The above copyright notice and this permission notice shall be included
3.19 +// in all copies or substantial portions of the Software.
3.20 +//
3.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
3.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
3.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
3.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
3.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
3.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
3.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
3.28 +// </copyright>
3.29 +// <summary>
3.30 +// Extension method used to convert to/from Windows/Windows.Media classes.
3.31 +// </summary>
3.32 +// --------------------------------------------------------------------------------------------------------------------
3.33 +namespace OxyPlot.WindowsForms
3.34 +{
3.35 + using System;
3.36 + using System.Drawing;
3.37 + using System.Windows.Forms;
3.38 +
3.39 + /// <summary>
3.40 + /// Extension method used to convert to/from Windows/Windows.Media classes.
3.41 + /// </summary>
3.42 + public static class ConverterExtensions
3.43 + {
3.44 + /// <summary>
3.45 + /// Calculate the distance between two points.
3.46 + /// </summary>
3.47 + /// <param name="p1">
3.48 + /// The first point.
3.49 + /// </param>
3.50 + /// <param name="p2">
3.51 + /// The second point.
3.52 + /// </param>
3.53 + /// <returns>
3.54 + /// The distance.
3.55 + /// </returns>
3.56 + public static double DistanceTo(this Point p1, Point p2)
3.57 + {
3.58 + double dx = p1.X - p2.X;
3.59 + double dy = p1.Y - p2.Y;
3.60 + return Math.Sqrt((dx * dx) + (dy * dy));
3.61 + }
3.62 +
3.63 + /// <summary>
3.64 + /// Converts a color to a Brush.
3.65 + /// </summary>
3.66 + /// <param name="c">
3.67 + /// The color.
3.68 + /// </param>
3.69 + /// <returns>
3.70 + /// A SolidColorBrush.
3.71 + /// </returns>
3.72 + public static Brush ToBrush(this OxyColor c)
3.73 + {
3.74 + return new SolidBrush(c.ToColor());
3.75 + }
3.76 +
3.77 + /// <summary>
3.78 + /// Converts an OxyColor to a Color.
3.79 + /// </summary>
3.80 + /// <param name="c">
3.81 + /// The color.
3.82 + /// </param>
3.83 + /// <returns>
3.84 + /// A Color.
3.85 + /// </returns>
3.86 + public static Color ToColor(this OxyColor c)
3.87 + {
3.88 + return Color.FromArgb(c.A, c.R, c.G, c.B);
3.89 + }
3.90 +
3.91 + /// <summary>
3.92 + /// Converts a HorizontalAlignment to a HorizontalTextAlign.
3.93 + /// </summary>
3.94 + /// <param name="alignment">
3.95 + /// The alignment.
3.96 + /// </param>
3.97 + /// <returns>
3.98 + /// A HorizontalTextAlign.
3.99 + /// </returns>
3.100 + public static OxyPlot.HorizontalAlignment ToHorizontalTextAlign(this HorizontalAlignment alignment)
3.101 + {
3.102 + switch (alignment)
3.103 + {
3.104 + case HorizontalAlignment.Center:
3.105 + return OxyPlot.HorizontalAlignment.Center;
3.106 + case HorizontalAlignment.Right:
3.107 + return OxyPlot.HorizontalAlignment.Right;
3.108 + default:
3.109 + return OxyPlot.HorizontalAlignment.Left;
3.110 + }
3.111 + }
3.112 +
3.113 + /// <summary>
3.114 + /// Converts a Color to an OxyColor.
3.115 + /// </summary>
3.116 + /// <param name="color">
3.117 + /// The color.
3.118 + /// </param>
3.119 + /// <returns>
3.120 + /// An OxyColor.
3.121 + /// </returns>
3.122 + public static OxyColor ToOxyColor(this Color color)
3.123 + {
3.124 + return OxyColor.FromArgb(color.A, color.R, color.G, color.B);
3.125 + }
3.126 +
3.127 + /// <summary>
3.128 + /// Converts a nullable Color to an OxyColor.
3.129 + /// </summary>
3.130 + /// <param name="color">
3.131 + /// The color.
3.132 + /// </param>
3.133 + /// <returns>
3.134 + /// An OxyColor.
3.135 + /// </returns>
3.136 + public static OxyColor ToOxyColor(this Color? color)
3.137 + {
3.138 + return color.HasValue ? color.Value.ToOxyColor() : null;
3.139 + }
3.140 +
3.141 + /// <summary>
3.142 + /// Converts a Brush to an OxyColor.
3.143 + /// </summary>
3.144 + /// <param name="brush">
3.145 + /// The brush.
3.146 + /// </param>
3.147 + /// <returns>
3.148 + /// An oxycolor.
3.149 + /// </returns>
3.150 + public static OxyColor ToOxyColor(this Brush brush)
3.151 + {
3.152 + var scb = brush as SolidBrush;
3.153 + return scb != null ? scb.Color.ToOxyColor() : null;
3.154 + }
3.155 +
3.156 + /// <summary>
3.157 + /// Converts a Thickness to an OxyThickness.
3.158 + /// </summary>
3.159 + /// <returns>
3.160 + /// An OxyPlot thickness.
3.161 + /// </returns>
3.162 + /// <summary>
3.163 + /// Converts a ScreenPoint to a Point.
3.164 + /// </summary>
3.165 + /// <param name="pt">
3.166 + /// The screen point.
3.167 + /// </param>
3.168 + /// <param name="aliased">
3.169 + /// use pixel alignment conversion if set to <c>true</c>.
3.170 + /// </param>
3.171 + /// <returns>
3.172 + /// A point.
3.173 + /// </returns>
3.174 + public static Point ToPoint(this ScreenPoint pt, bool aliased)
3.175 + {
3.176 + // adding 0.5 to get pixel boundary alignment, seems to work
3.177 + // http://weblogs.asp.net/mschwarz/archive/2008/01/04/silverlight-rectangles-paths-and-line-comparison.aspx
3.178 + // http://www.wynapse.com/Silverlight/Tutor/Silverlight_Rectangles_Paths_And_Lines_Comparison.aspx
3.179 + if (aliased)
3.180 + {
3.181 + return new Point((int)pt.X, (int)pt.Y);
3.182 + }
3.183 +
3.184 + return new Point((int)Math.Round(pt.X), (int)Math.Round(pt.Y));
3.185 + }
3.186 +
3.187 + /// <summary>
3.188 + /// Converts an OxyRect to a Rect.
3.189 + /// </summary>
3.190 + /// <param name="r">
3.191 + /// The rectangle.
3.192 + /// </param>
3.193 + /// <param name="aliased">
3.194 + /// use pixel alignment if set to <c>true</c>.
3.195 + /// </param>
3.196 + /// <returns>
3.197 + /// A rect.
3.198 + /// </returns>
3.199 + public static Rectangle ToRect(this OxyRect r, bool aliased)
3.200 + {
3.201 + if (aliased)
3.202 + {
3.203 + var x = (int)r.Left;
3.204 + var y = (int)r.Top;
3.205 + var ri = (int)r.Right;
3.206 + var bo = (int)r.Bottom;
3.207 + return new Rectangle(x, y, ri - x, bo - y);
3.208 + }
3.209 +
3.210 + return new Rectangle(
3.211 + (int)Math.Round(r.Left), (int)Math.Round(r.Top), (int)Math.Round(r.Width), (int)Math.Round(r.Height));
3.212 + }
3.213 +
3.214 + /// <summary>
3.215 + /// Converts a point to a ScreenPoint.
3.216 + /// </summary>
3.217 + /// <param name="pt">
3.218 + /// The point.
3.219 + /// </param>
3.220 + /// <returns>
3.221 + /// A screen point.
3.222 + /// </returns>
3.223 + public static ScreenPoint ToScreenPoint(this Point pt)
3.224 + {
3.225 + return new ScreenPoint(pt.X, pt.Y);
3.226 + }
3.227 +
3.228 + /// <summary>
3.229 + /// Converts a Point array to a ScreenPoint array.
3.230 + /// </summary>
3.231 + /// <param name="points">
3.232 + /// The points.
3.233 + /// </param>
3.234 + /// <returns>
3.235 + /// A ScreenPoint array.
3.236 + /// </returns>
3.237 + public static ScreenPoint[] ToScreenPointArray(this Point[] points)
3.238 + {
3.239 + if (points == null)
3.240 + {
3.241 + return null;
3.242 + }
3.243 +
3.244 + var pts = new ScreenPoint[points.Length];
3.245 + for (int i = 0; i < points.Length; i++)
3.246 + {
3.247 + pts[i] = points[i].ToScreenPoint();
3.248 + }
3.249 +
3.250 + return pts;
3.251 + }
3.252 +
3.253 + }
3.254 +}
3.255 \ No newline at end of file
4.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
4.2 +++ b/External/OxyPlot/OxyPlot.WindowsForms/NamespaceDoc.cs Sat Jun 08 16:53:22 2013 +0000
4.3 @@ -0,0 +1,37 @@
4.4 +// --------------------------------------------------------------------------------------------------------------------
4.5 +// <copyright file="NamespaceDoc.cs" company="OxyPlot">
4.6 +// The MIT License (MIT)
4.7 +//
4.8 +// Copyright (c) 2012 Oystein Bjorke
4.9 +//
4.10 +// Permission is hereby granted, free of charge, to any person obtaining a
4.11 +// copy of this software and associated documentation files (the
4.12 +// "Software"), to deal in the Software without restriction, including
4.13 +// without limitation the rights to use, copy, modify, merge, publish,
4.14 +// distribute, sublicense, and/or sell copies of the Software, and to
4.15 +// permit persons to whom the Software is furnished to do so, subject to
4.16 +// the following conditions:
4.17 +//
4.18 +// The above copyright notice and this permission notice shall be included
4.19 +// in all copies or substantial portions of the Software.
4.20 +//
4.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
4.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
4.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
4.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
4.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
4.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
4.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
4.28 +// </copyright>
4.29 +// --------------------------------------------------------------------------------------------------------------------
4.30 +
4.31 +namespace OxyPlot.WindowsForms
4.32 +{
4.33 + /// <summary>
4.34 + /// The OxyPlot.WindowsForms namespace contains controls for Windows Forms and a bitmap exporter.
4.35 + /// </summary>
4.36 + [System.Runtime.CompilerServices.CompilerGenerated]
4.37 + internal class NamespaceDoc
4.38 + {
4.39 + }
4.40 +}
4.41 \ No newline at end of file
5.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
5.2 +++ b/External/OxyPlot/OxyPlot.WindowsForms/OxyPlot.WindowsForms.csproj Sat Jun 08 16:53:22 2013 +0000
5.3 @@ -0,0 +1,79 @@
5.4 +<?xml version="1.0" encoding="utf-8"?>
5.5 +<Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
5.6 + <Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
5.7 + <PropertyGroup>
5.8 + <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
5.9 + <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
5.10 + <ProjectGuid>{D4554296-094E-4CAC-8EAE-44EB250666C6}</ProjectGuid>
5.11 + <OutputType>Library</OutputType>
5.12 + <AppDesignerFolder>Properties</AppDesignerFolder>
5.13 + <RootNamespace>OxyPlot.WindowsForms</RootNamespace>
5.14 + <AssemblyName>OxyPlot.WindowsForms</AssemblyName>
5.15 + <TargetFrameworkVersion>v4.0</TargetFrameworkVersion>
5.16 + <TargetFrameworkProfile>Client</TargetFrameworkProfile>
5.17 + <FileAlignment>512</FileAlignment>
5.18 + </PropertyGroup>
5.19 + <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
5.20 + <DebugSymbols>true</DebugSymbols>
5.21 + <DebugType>full</DebugType>
5.22 + <Optimize>false</Optimize>
5.23 + <OutputPath>bin\Debug\NET40\</OutputPath>
5.24 + <IntermediateOutputPath>obj\Debug\NET40\</IntermediateOutputPath>
5.25 + <DefineConstants>DEBUG;TRACE</DefineConstants>
5.26 + <ErrorReport>prompt</ErrorReport>
5.27 + <WarningLevel>4</WarningLevel>
5.28 + </PropertyGroup>
5.29 + <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
5.30 + <DebugType>pdbonly</DebugType>
5.31 + <Optimize>true</Optimize>
5.32 + <OutputPath>..\..\Output\NET40\</OutputPath>
5.33 + <IntermediateOutputPath>obj\Release\NET40\</IntermediateOutputPath>
5.34 + <DefineConstants>TRACE</DefineConstants>
5.35 + <ErrorReport>prompt</ErrorReport>
5.36 + <WarningLevel>4</WarningLevel>
5.37 + <DocumentationFile>..\..\Output\NET40\OxyPlot.WindowsForms.XML</DocumentationFile>
5.38 + </PropertyGroup>
5.39 + <PropertyGroup>
5.40 + <SignAssembly>true</SignAssembly>
5.41 + </PropertyGroup>
5.42 + <PropertyGroup>
5.43 + <AssemblyOriginatorKeyFile>OxyPlot.WindowsForms.snk</AssemblyOriginatorKeyFile>
5.44 + </PropertyGroup>
5.45 + <ItemGroup>
5.46 + <Reference Include="System" />
5.47 + <Reference Include="System.Core" />
5.48 + <Reference Include="System.Drawing" />
5.49 + <Reference Include="System.Windows.Forms" />
5.50 + </ItemGroup>
5.51 + <ItemGroup>
5.52 + <Compile Include="..\GlobalAssemblyInfo.cs">
5.53 + <Link>Properties\GlobalAssemblyInfo.cs</Link>
5.54 + </Compile>
5.55 + <Compile Include="Helpers\ConverterExtensions.cs" />
5.56 + <Compile Include="GraphicsRenderContext.cs" />
5.57 + <Compile Include="NamespaceDoc.cs" />
5.58 + <Compile Include="Plot.cs">
5.59 + <SubType>Component</SubType>
5.60 + </Compile>
5.61 + <Compile Include="PngExporter.cs" />
5.62 + <Compile Include="Properties\AssemblyInfo.cs" />
5.63 + <Service Include="{94E38DFF-614B-4cbd-B67C-F211BB35CE8B}" />
5.64 + </ItemGroup>
5.65 + <ItemGroup>
5.66 + <None Include="OxyPlot.WindowsForms.snk" />
5.67 + </ItemGroup>
5.68 + <ItemGroup>
5.69 + <ProjectReference Include="..\OxyPlot\OxyPlot.csproj">
5.70 + <Project>{7a0b35c0-dd17-4964-8e9a-44d6cecdc692}</Project>
5.71 + <Name>OxyPlot</Name>
5.72 + </ProjectReference>
5.73 + </ItemGroup>
5.74 + <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
5.75 + <!-- To modify your build process, add your task inside one of the targets below and uncomment it.
5.76 + Other similar extension points exist, see Microsoft.Common.targets.
5.77 + <Target Name="BeforeBuild">
5.78 + </Target>
5.79 + <Target Name="AfterBuild">
5.80 + </Target>
5.81 + -->
5.82 +</Project>
5.83 \ No newline at end of file
6.1 Binary file External/OxyPlot/OxyPlot.WindowsForms/OxyPlot.WindowsForms.snk has changed
7.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
7.2 +++ b/External/OxyPlot/OxyPlot.WindowsForms/Plot.cs Sat Jun 08 16:53:22 2013 +0000
7.3 @@ -0,0 +1,897 @@
7.4 +// --------------------------------------------------------------------------------------------------------------------
7.5 +// <copyright file="Plot.cs" company="OxyPlot">
7.6 +// The MIT License (MIT)
7.7 +//
7.8 +// Copyright (c) 2012 Oystein Bjorke
7.9 +//
7.10 +// Permission is hereby granted, free of charge, to any person obtaining a
7.11 +// copy of this software and associated documentation files (the
7.12 +// "Software"), to deal in the Software without restriction, including
7.13 +// without limitation the rights to use, copy, modify, merge, publish,
7.14 +// distribute, sublicense, and/or sell copies of the Software, and to
7.15 +// permit persons to whom the Software is furnished to do so, subject to
7.16 +// the following conditions:
7.17 +//
7.18 +// The above copyright notice and this permission notice shall be included
7.19 +// in all copies or substantial portions of the Software.
7.20 +//
7.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
7.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
7.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
7.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
7.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
7.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
7.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
7.28 +// </copyright>
7.29 +// <summary>
7.30 +// Represents a control that displays a plot.
7.31 +// </summary>
7.32 +// --------------------------------------------------------------------------------------------------------------------
7.33 +namespace OxyPlot.WindowsForms
7.34 +{
7.35 + using System;
7.36 + using System.ComponentModel;
7.37 + using System.Diagnostics;
7.38 + using System.Drawing;
7.39 + using System.Runtime.InteropServices;
7.40 + using System.Windows.Forms;
7.41 +
7.42 + using OxyPlot.Axes;
7.43 + using OxyPlot.Series;
7.44 +
7.45 + /// <summary>
7.46 + /// Represents a control that displays a plot.
7.47 + /// </summary>
7.48 + [Serializable]
7.49 + public class Plot : Control, IPlotControl
7.50 + {
7.51 + /// <summary>
7.52 + /// The category for the properties of this control.
7.53 + /// </summary>
7.54 + private const string OxyPlotCategory = "OxyPlot";
7.55 +
7.56 + /// <summary>
7.57 + /// The invalidate lock.
7.58 + /// </summary>
7.59 + private readonly object invalidateLock = new object();
7.60 +
7.61 + /// <summary>
7.62 + /// The model lock.
7.63 + /// </summary>
7.64 + private readonly object modelLock = new object();
7.65 +
7.66 + /// <summary>
7.67 + /// The rendering lock.
7.68 + /// </summary>
7.69 + private readonly object renderingLock = new object();
7.70 +
7.71 + /// <summary>
7.72 + /// The current model (holding a reference to this plot control).
7.73 + /// </summary>
7.74 + [NonSerialized]
7.75 + private PlotModel currentModel;
7.76 +
7.77 + /// <summary>
7.78 + /// The is model invalidated.
7.79 + /// </summary>
7.80 + private bool isModelInvalidated;
7.81 +
7.82 + /// <summary>
7.83 + /// The model.
7.84 + /// </summary>
7.85 + private PlotModel model;
7.86 +
7.87 + /// <summary>
7.88 + /// The mouse manipulator.
7.89 + /// </summary>
7.90 + [NonSerialized]
7.91 + private ManipulatorBase mouseManipulator;
7.92 +
7.93 + /// <summary>
7.94 + /// The update data flag.
7.95 + /// </summary>
7.96 + private bool updateDataFlag = true;
7.97 +
7.98 + /// <summary>
7.99 + /// The zoom rectangle.
7.100 + /// </summary>
7.101 + private Rectangle zoomRectangle;
7.102 +
7.103 + /// <summary>
7.104 + /// The render context.
7.105 + /// </summary>
7.106 + private GraphicsRenderContext renderContext;
7.107 +
7.108 + /// <summary>
7.109 + /// Initializes a new instance of the <see cref="Plot"/> class.
7.110 + /// </summary>
7.111 + public Plot()
7.112 + {
7.113 + this.renderContext = new GraphicsRenderContext();
7.114 +
7.115 + // ReSharper disable DoNotCallOverridableMethodsInConstructor
7.116 + this.DoubleBuffered = true;
7.117 + // ReSharper restore DoNotCallOverridableMethodsInConstructor
7.118 + this.KeyboardPanHorizontalStep = 0.1;
7.119 + this.KeyboardPanVerticalStep = 0.1;
7.120 + this.PanCursor = Cursors.Hand;
7.121 + this.ZoomRectangleCursor = Cursors.SizeNWSE;
7.122 + this.ZoomHorizontalCursor = Cursors.SizeWE;
7.123 + this.ZoomVerticalCursor = Cursors.SizeNS;
7.124 + }
7.125 +
7.126 + /// <summary>
7.127 + /// Gets the actual model.
7.128 + /// </summary>
7.129 + /// <value> The actual model. </value>
7.130 + public PlotModel ActualModel
7.131 + {
7.132 + get
7.133 + {
7.134 + return this.Model;
7.135 + }
7.136 + }
7.137 +
7.138 + /// <summary>
7.139 + /// Gets or sets the keyboard pan horizontal step.
7.140 + /// </summary>
7.141 + /// <value> The keyboard pan horizontal step. </value>
7.142 + [Category(OxyPlotCategory)]
7.143 + public double KeyboardPanHorizontalStep { get; set; }
7.144 +
7.145 + /// <summary>
7.146 + /// Gets or sets the keyboard pan vertical step.
7.147 + /// </summary>
7.148 + /// <value> The keyboard pan vertical step. </value>
7.149 + [Category(OxyPlotCategory)]
7.150 + public double KeyboardPanVerticalStep { get; set; }
7.151 +
7.152 + /// <summary>
7.153 + /// Gets or sets the model.
7.154 + /// </summary>
7.155 + [Browsable(false)]
7.156 + [DefaultValue(null)]
7.157 + [Category(OxyPlotCategory)]
7.158 + public PlotModel Model
7.159 + {
7.160 + get
7.161 + {
7.162 + return this.model;
7.163 + }
7.164 +
7.165 + set
7.166 + {
7.167 + if (this.model != value)
7.168 + {
7.169 + this.model = value;
7.170 + this.OnModelChanged();
7.171 + }
7.172 + }
7.173 + }
7.174 +
7.175 + /// <summary>
7.176 + /// Gets or sets the pan cursor.
7.177 + /// </summary>
7.178 + [Category(OxyPlotCategory)]
7.179 + public Cursor PanCursor { get; set; }
7.180 +
7.181 + /// <summary>
7.182 + /// Gets or sets the horizontal zoom cursor.
7.183 + /// </summary>
7.184 + [Category(OxyPlotCategory)]
7.185 + public Cursor ZoomHorizontalCursor { get; set; }
7.186 +
7.187 + /// <summary>
7.188 + /// Gets or sets the rectangle zoom cursor.
7.189 + /// </summary>
7.190 + [Category(OxyPlotCategory)]
7.191 + public Cursor ZoomRectangleCursor { get; set; }
7.192 +
7.193 + /// <summary>
7.194 + /// Gets or sets vertical zoom cursor.
7.195 + /// </summary>
7.196 + [Category(OxyPlotCategory)]
7.197 + public Cursor ZoomVerticalCursor { get; set; }
7.198 +
7.199 + /// <summary>
7.200 + /// Get the axes from a point.
7.201 + /// </summary>
7.202 + /// <param name="pt">
7.203 + /// The point.
7.204 + /// </param>
7.205 + /// <param name="xaxis">
7.206 + /// The x axis.
7.207 + /// </param>
7.208 + /// <param name="yaxis">
7.209 + /// The y axis.
7.210 + /// </param>
7.211 + public void GetAxesFromPoint(ScreenPoint pt, out Axis xaxis, out Axis yaxis)
7.212 + {
7.213 + if (this.Model == null)
7.214 + {
7.215 + xaxis = null;
7.216 + yaxis = null;
7.217 + return;
7.218 + }
7.219 +
7.220 + this.Model.GetAxesFromPoint(pt, out xaxis, out yaxis);
7.221 + }
7.222 +
7.223 + /// <summary>
7.224 + /// Get the series from a point.
7.225 + /// </summary>
7.226 + /// <param name="pt">
7.227 + /// The point (screen coordinates).
7.228 + /// </param>
7.229 + /// <param name="limit">
7.230 + /// The limit.
7.231 + /// </param>
7.232 + /// <returns>
7.233 + /// The series.
7.234 + /// </returns>
7.235 + public Series GetSeriesFromPoint(ScreenPoint pt, double limit)
7.236 + {
7.237 + if (this.Model == null)
7.238 + {
7.239 + return null;
7.240 + }
7.241 +
7.242 + return this.Model.GetSeriesFromPoint(pt, limit);
7.243 + }
7.244 +
7.245 + /// <summary>
7.246 + /// The hide tracker.
7.247 + /// </summary>
7.248 + public void HideTracker()
7.249 + {
7.250 + }
7.251 +
7.252 + /// <summary>
7.253 + /// The hide zoom rectangle.
7.254 + /// </summary>
7.255 + public void HideZoomRectangle()
7.256 + {
7.257 + this.zoomRectangle = Rectangle.Empty;
7.258 + this.Invalidate();
7.259 + }
7.260 +
7.261 + /// <summary>
7.262 + /// The invalidate plot.
7.263 + /// </summary>
7.264 + /// <param name="updateData">
7.265 + /// The update data.
7.266 + /// </param>
7.267 + public void InvalidatePlot(bool updateData)
7.268 + {
7.269 + lock (this.invalidateLock)
7.270 + {
7.271 + this.isModelInvalidated = true;
7.272 + this.updateDataFlag = this.updateDataFlag || updateData;
7.273 + }
7.274 +
7.275 + this.Invalidate();
7.276 + }
7.277 +
7.278 + /// <summary>
7.279 + /// Called when the Model property has been changed.
7.280 + /// </summary>
7.281 + public void OnModelChanged()
7.282 + {
7.283 + lock (this.modelLock)
7.284 + {
7.285 + if (this.currentModel != null)
7.286 + {
7.287 + this.currentModel.AttachPlotControl(null);
7.288 + }
7.289 +
7.290 + if (this.Model != null)
7.291 + {
7.292 + if (this.Model.PlotControl != null)
7.293 + {
7.294 + throw new InvalidOperationException(
7.295 + "This PlotModel is already in use by some other plot control.");
7.296 + }
7.297 +
7.298 + this.Model.AttachPlotControl(this);
7.299 + this.currentModel = this.Model;
7.300 + }
7.301 + }
7.302 +
7.303 + this.InvalidatePlot(true);
7.304 + }
7.305 +
7.306 + /// <summary>
7.307 + /// The pan.
7.308 + /// </summary>
7.309 + /// <param name="axis">
7.310 + /// The axis.
7.311 + /// </param>
7.312 + /// <param name="x0">
7.313 + /// The x 0.
7.314 + /// </param>
7.315 + /// <param name="x1">
7.316 + /// The x 1.
7.317 + /// </param>
7.318 + public void Pan(Axis axis, ScreenPoint x0, ScreenPoint x1)
7.319 + {
7.320 + axis.Pan(x0, x1);
7.321 + this.InvalidatePlot(false);
7.322 + }
7.323 +
7.324 + /// <summary>
7.325 + /// Pans all axes.
7.326 + /// </summary>
7.327 + /// <param name="deltax">
7.328 + /// The horizontal delta.
7.329 + /// </param>
7.330 + /// <param name="deltay">
7.331 + /// The vertical delta.
7.332 + /// </param>
7.333 + public void PanAll(double deltax, double deltay)
7.334 + {
7.335 + foreach (var a in this.ActualModel.Axes)
7.336 + {
7.337 + a.Pan(a.IsHorizontal() ? deltax : deltay);
7.338 + }
7.339 +
7.340 + this.InvalidatePlot(false);
7.341 + }
7.342 +
7.343 + /// <summary>
7.344 + /// The refresh plot.
7.345 + /// </summary>
7.346 + /// <param name="updateData">
7.347 + /// The update data.
7.348 + /// </param>
7.349 + public void RefreshPlot(bool updateData)
7.350 + {
7.351 + lock (this.invalidateLock)
7.352 + {
7.353 + this.isModelInvalidated = true;
7.354 + this.updateDataFlag = this.updateDataFlag || updateData;
7.355 + }
7.356 +
7.357 + this.Refresh();
7.358 + }
7.359 +
7.360 + /// <summary>
7.361 + /// The reset.
7.362 + /// </summary>
7.363 + /// <param name="axis">
7.364 + /// The axis.
7.365 + /// </param>
7.366 + public void Reset(Axis axis)
7.367 + {
7.368 + axis.Reset();
7.369 + this.InvalidatePlot(false);
7.370 + }
7.371 +
7.372 + /// <summary>
7.373 + /// Sets the cursor type.
7.374 + /// </summary>
7.375 + /// <param name="cursorType">
7.376 + /// The cursor type.
7.377 + /// </param>
7.378 + public void SetCursorType(CursorType cursorType)
7.379 + {
7.380 + switch (cursorType)
7.381 + {
7.382 + case CursorType.Pan:
7.383 + this.Cursor = this.PanCursor;
7.384 + break;
7.385 + case CursorType.ZoomRectangle:
7.386 + this.Cursor = this.ZoomRectangleCursor;
7.387 + break;
7.388 + case CursorType.ZoomHorizontal:
7.389 + this.Cursor = this.ZoomHorizontalCursor;
7.390 + break;
7.391 + case CursorType.ZoomVertical:
7.392 + this.Cursor = this.ZoomVerticalCursor;
7.393 + break;
7.394 + default:
7.395 + this.Cursor = Cursors.Arrow;
7.396 + break;
7.397 + }
7.398 + }
7.399 +
7.400 + /// <summary>
7.401 + /// The show tracker.
7.402 + /// </summary>
7.403 + /// <param name="data">
7.404 + /// The data.
7.405 + /// </param>
7.406 + public void ShowTracker(TrackerHitResult data)
7.407 + {
7.408 + // not implemented for WindowsForms
7.409 + }
7.410 +
7.411 + /// <summary>
7.412 + /// The show zoom rectangle.
7.413 + /// </summary>
7.414 + /// <param name="r">
7.415 + /// The r.
7.416 + /// </param>
7.417 + public void ShowZoomRectangle(OxyRect r)
7.418 + {
7.419 + this.zoomRectangle = new Rectangle((int)r.Left, (int)r.Top, (int)r.Width, (int)r.Height);
7.420 + this.Invalidate();
7.421 + }
7.422 +
7.423 + /// <summary>
7.424 + /// The zoom.
7.425 + /// </summary>
7.426 + /// <param name="axis">
7.427 + /// The axis.
7.428 + /// </param>
7.429 + /// <param name="p1">
7.430 + /// The p 1.
7.431 + /// </param>
7.432 + /// <param name="p2">
7.433 + /// The p 2.
7.434 + /// </param>
7.435 + public void Zoom(Axis axis, double p1, double p2)
7.436 + {
7.437 + axis.Zoom(p1, p2);
7.438 + this.InvalidatePlot(false);
7.439 + }
7.440 +
7.441 + /// <summary>
7.442 + /// The zoom all.
7.443 + /// </summary>
7.444 + public void ZoomAll()
7.445 + {
7.446 + foreach (var a in this.Model.Axes)
7.447 + {
7.448 + a.Reset();
7.449 + }
7.450 +
7.451 + this.InvalidatePlot(false);
7.452 + }
7.453 +
7.454 + /// <summary>
7.455 + /// Zooms all axes.
7.456 + /// </summary>
7.457 + /// <param name="delta">
7.458 + /// The delta.
7.459 + /// </param>
7.460 + public void ZoomAllAxes(double delta)
7.461 + {
7.462 + foreach (var a in this.ActualModel.Axes)
7.463 + {
7.464 + this.ZoomAt(a, delta);
7.465 + }
7.466 +
7.467 + this.RefreshPlot(false);
7.468 + }
7.469 +
7.470 + /// <summary>
7.471 + /// The zoom at.
7.472 + /// </summary>
7.473 + /// <param name="axis">
7.474 + /// The axis.
7.475 + /// </param>
7.476 + /// <param name="factor">
7.477 + /// The factor.
7.478 + /// </param>
7.479 + /// <param name="x">
7.480 + /// The x.
7.481 + /// </param>
7.482 + public void ZoomAt(Axis axis, double factor, double x = double.NaN)
7.483 + {
7.484 + if (double.IsNaN(x))
7.485 + {
7.486 + double sx = (axis.Transform(axis.ActualMaximum) + axis.Transform(axis.ActualMinimum)) * 0.5;
7.487 + x = axis.InverseTransform(sx);
7.488 + }
7.489 +
7.490 + axis.ZoomAt(factor, x);
7.491 + this.InvalidatePlot(false);
7.492 + }
7.493 +
7.494 + /// <summary>
7.495 + /// The on mouse down.
7.496 + /// </summary>
7.497 + /// <param name="e">
7.498 + /// The e.
7.499 + /// </param>
7.500 + protected override void OnMouseDown(MouseEventArgs e)
7.501 + {
7.502 + base.OnMouseDown(e);
7.503 +
7.504 + if (this.mouseManipulator != null)
7.505 + {
7.506 + return;
7.507 + }
7.508 +
7.509 + this.Focus();
7.510 + this.Capture = true;
7.511 +
7.512 + if (this.ActualModel != null)
7.513 + {
7.514 + var args = this.CreateMouseEventArgs(e);
7.515 + this.ActualModel.HandleMouseDown(this, args);
7.516 + if (args.Handled)
7.517 + {
7.518 + return;
7.519 + }
7.520 + }
7.521 +
7.522 + this.mouseManipulator = this.GetManipulator(e);
7.523 +
7.524 + if (this.mouseManipulator != null)
7.525 + {
7.526 + this.mouseManipulator.Started(this.CreateManipulationEventArgs(e));
7.527 + }
7.528 + }
7.529 +
7.530 + /// <summary>
7.531 + /// The on mouse move.
7.532 + /// </summary>
7.533 + /// <param name="e">
7.534 + /// The e.
7.535 + /// </param>
7.536 + protected override void OnMouseMove(MouseEventArgs e)
7.537 + {
7.538 + base.OnMouseMove(e);
7.539 +
7.540 + if (this.ActualModel != null)
7.541 + {
7.542 + var args = this.CreateMouseEventArgs(e);
7.543 + this.ActualModel.HandleMouseMove(this, args);
7.544 + if (args.Handled)
7.545 + {
7.546 + return;
7.547 + }
7.548 + }
7.549 +
7.550 + if (this.mouseManipulator != null)
7.551 + {
7.552 + this.mouseManipulator.Delta(this.CreateManipulationEventArgs(e));
7.553 + }
7.554 + }
7.555 +
7.556 + /// <summary>
7.557 + /// Raises the <see cref="E:System.Windows.Forms.Control.MouseUp"/> event.
7.558 + /// </summary>
7.559 + /// <param name="e">
7.560 + /// A <see cref="T:System.Windows.Forms.MouseEventArgs"/> that contains the event data.
7.561 + /// </param>
7.562 + protected override void OnMouseUp(MouseEventArgs e)
7.563 + {
7.564 + base.OnMouseUp(e);
7.565 + this.Capture = false;
7.566 +
7.567 + if (this.ActualModel != null)
7.568 + {
7.569 + var args = this.CreateMouseEventArgs(e);
7.570 + this.ActualModel.HandleMouseUp(this, args);
7.571 + if (args.Handled)
7.572 + {
7.573 + return;
7.574 + }
7.575 + }
7.576 +
7.577 + if (this.mouseManipulator != null)
7.578 + {
7.579 + this.mouseManipulator.Completed(this.CreateManipulationEventArgs(e));
7.580 + }
7.581 +
7.582 + this.mouseManipulator = null;
7.583 + }
7.584 +
7.585 + /// <summary>
7.586 + /// Raises the <see cref="E:System.Windows.Forms.Control.MouseWheel"/> event.
7.587 + /// </summary>
7.588 + /// <param name="e">
7.589 + /// A <see cref="T:System.Windows.Forms.MouseEventArgs"/> that contains the event data.
7.590 + /// </param>
7.591 + protected override void OnMouseWheel(MouseEventArgs e)
7.592 + {
7.593 + base.OnMouseWheel(e);
7.594 + bool isControlDown = ModifierKeys == Keys.Control;
7.595 + var m = new ZoomStepManipulator(this, e.Delta * 0.001, isControlDown);
7.596 + m.Started(new ManipulationEventArgs(e.Location.ToScreenPoint()));
7.597 + }
7.598 +
7.599 + /// <summary>
7.600 + /// Raises the <see cref="E:System.Windows.Forms.Control.Paint"/> event.
7.601 + /// </summary>
7.602 + /// <param name="e">
7.603 + /// A <see cref="T:System.Windows.Forms.PaintEventArgs"/> that contains the event data.
7.604 + /// </param>
7.605 + protected override void OnPaint(PaintEventArgs e)
7.606 + {
7.607 + base.OnPaint(e);
7.608 + try
7.609 + {
7.610 + lock (this.invalidateLock)
7.611 + {
7.612 + if (this.isModelInvalidated)
7.613 + {
7.614 + if (this.model != null)
7.615 + {
7.616 + this.model.Update(this.updateDataFlag);
7.617 + this.updateDataFlag = false;
7.618 + }
7.619 +
7.620 + this.isModelInvalidated = false;
7.621 + }
7.622 + }
7.623 +
7.624 + lock (this.renderingLock)
7.625 + {
7.626 + this.renderContext.SetGraphicsTarget(e.Graphics);
7.627 + if (this.model != null)
7.628 + {
7.629 + this.model.Render(this.renderContext, this.Width, this.Height);
7.630 + }
7.631 +
7.632 + if (this.zoomRectangle != Rectangle.Empty)
7.633 + {
7.634 + using (var zoomBrush = new SolidBrush(Color.FromArgb(0x40, 0xFF, 0xFF, 0x00)))
7.635 + using (var zoomPen = new Pen(Color.Black))
7.636 + {
7.637 + zoomPen.DashPattern = new float[] { 3, 1 };
7.638 + e.Graphics.FillRectangle(zoomBrush, this.zoomRectangle);
7.639 + e.Graphics.DrawRectangle(zoomPen, this.zoomRectangle);
7.640 + }
7.641 + }
7.642 + }
7.643 + }
7.644 + catch (Exception paintException)
7.645 + {
7.646 + var trace = new StackTrace(paintException);
7.647 + Debug.WriteLine(paintException);
7.648 + Debug.WriteLine(trace);
7.649 + using (var font = new Font("Arial", 10))
7.650 + {
7.651 + e.Graphics.DrawString(
7.652 + "OxyPlot paint exception: " + paintException.Message, font, Brushes.Red, 10, 10);
7.653 + }
7.654 + }
7.655 + }
7.656 +
7.657 + /// <summary>
7.658 + /// Raises the <see cref="E:System.Windows.Forms.Control.PreviewKeyDown"/> event.
7.659 + /// </summary>
7.660 + /// <param name="e">
7.661 + /// A <see cref="T:System.Windows.Forms.PreviewKeyDownEventArgs"/> that contains the event data.
7.662 + /// </param>
7.663 + protected override void OnPreviewKeyDown(PreviewKeyDownEventArgs e)
7.664 + {
7.665 + base.OnPreviewKeyDown(e);
7.666 + if (e.KeyCode == Keys.A)
7.667 + {
7.668 + this.ZoomAll();
7.669 + }
7.670 +
7.671 + bool control = (e.Modifiers & Keys.Control) == Keys.Control;
7.672 + bool alt = (e.Modifiers & Keys.Alt) == Keys.Alt;
7.673 +
7.674 + double deltax = 0;
7.675 + double deltay = 0;
7.676 + double zoom = 0;
7.677 + switch (e.KeyCode)
7.678 + {
7.679 + case Keys.Up:
7.680 + deltay = -1;
7.681 + break;
7.682 + case Keys.Down:
7.683 + deltay = 1;
7.684 + break;
7.685 + case Keys.Left:
7.686 + deltax = -1;
7.687 + break;
7.688 + case Keys.Right:
7.689 + deltax = 1;
7.690 + break;
7.691 + case Keys.Add:
7.692 + case Keys.Oemplus:
7.693 + case Keys.PageUp:
7.694 + zoom = 1;
7.695 + break;
7.696 + case Keys.Subtract:
7.697 + case Keys.OemMinus:
7.698 + case Keys.PageDown:
7.699 + zoom = -1;
7.700 + break;
7.701 + }
7.702 +
7.703 + if ((deltax * deltax) + (deltay * deltay) > 0)
7.704 + {
7.705 + deltax = deltax * this.ActualModel.PlotArea.Width * this.KeyboardPanHorizontalStep;
7.706 + deltay = deltay * this.ActualModel.PlotArea.Height * this.KeyboardPanVerticalStep;
7.707 +
7.708 + // small steps if the user is pressing control
7.709 + if (control)
7.710 + {
7.711 + deltax *= 0.2;
7.712 + deltay *= 0.2;
7.713 + }
7.714 +
7.715 + this.PanAll(deltax, deltay);
7.716 +
7.717 + // e.Handled = true;
7.718 + }
7.719 +
7.720 + if (Math.Abs(zoom) > 1e-8)
7.721 + {
7.722 + if (control)
7.723 + {
7.724 + zoom *= 0.2;
7.725 + }
7.726 +
7.727 + this.ZoomAllAxes(1 + (zoom * 0.12));
7.728 +
7.729 + // e.Handled = true;
7.730 + }
7.731 +
7.732 + if (control && alt && this.ActualModel != null)
7.733 + {
7.734 + switch (e.KeyCode)
7.735 + {
7.736 + case Keys.R:
7.737 + this.SetClipboardText(this.ActualModel.CreateTextReport());
7.738 + break;
7.739 + case Keys.C:
7.740 + this.SetClipboardText(this.ActualModel.ToCode());
7.741 + break;
7.742 + case Keys.X:
7.743 +
7.744 + // this.SetClipboardText(this.ActualModel.ToXml());
7.745 + break;
7.746 + }
7.747 + }
7.748 + }
7.749 +
7.750 + /// <summary>
7.751 + /// Raises the <see cref="E:System.Windows.Forms.Control.Resize"/> event.
7.752 + /// </summary>
7.753 + /// <param name="e">
7.754 + /// An <see cref="T:System.EventArgs"/> that contains the event data.
7.755 + /// </param>
7.756 + protected override void OnResize(EventArgs e)
7.757 + {
7.758 + base.OnResize(e);
7.759 + this.InvalidatePlot(false);
7.760 + }
7.761 +
7.762 + /// <summary>
7.763 + /// Converts the changed button.
7.764 + /// </summary>
7.765 + /// <param name="e">
7.766 + /// The <see cref="System.Windows.Forms.MouseEventArgs"/> instance containing the event data.
7.767 + /// </param>
7.768 + /// <returns>
7.769 + /// The mouse button.
7.770 + /// </returns>
7.771 + private static OxyMouseButton ConvertChangedButton(MouseEventArgs e)
7.772 + {
7.773 + switch (e.Button)
7.774 + {
7.775 + case MouseButtons.Left:
7.776 + return OxyMouseButton.Left;
7.777 + case MouseButtons.Middle:
7.778 + return OxyMouseButton.Middle;
7.779 + case MouseButtons.Right:
7.780 + return OxyMouseButton.Right;
7.781 + case MouseButtons.XButton1:
7.782 + return OxyMouseButton.XButton1;
7.783 + case MouseButtons.XButton2:
7.784 + return OxyMouseButton.XButton2;
7.785 + }
7.786 +
7.787 + return OxyMouseButton.Left;
7.788 + }
7.789 +
7.790 + /// <summary>
7.791 + /// Creates the mouse event arguments.
7.792 + /// </summary>
7.793 + /// <param name="e">
7.794 + /// The <see cref="System.Windows.Forms.MouseEventArgs"/> instance containing the event data.
7.795 + /// </param>
7.796 + /// <returns>
7.797 + /// Mouse event arguments.
7.798 + /// </returns>
7.799 + private OxyMouseEventArgs CreateMouseEventArgs(MouseEventArgs e)
7.800 + {
7.801 + return new OxyMouseEventArgs
7.802 + {
7.803 + ChangedButton = ConvertChangedButton(e),
7.804 + Position = new ScreenPoint(e.Location.X, e.Location.Y),
7.805 + IsShiftDown = (ModifierKeys & Keys.Shift) == Keys.Shift,
7.806 + IsControlDown = (ModifierKeys & Keys.Control) == Keys.Control,
7.807 + IsAltDown = (ModifierKeys & Keys.Alt) == Keys.Alt,
7.808 + };
7.809 + }
7.810 +
7.811 + /// <summary>
7.812 + /// Creates the manipulation event args.
7.813 + /// </summary>
7.814 + /// <param name="e">
7.815 + /// The MouseEventArgs instance containing the event data.
7.816 + /// </param>
7.817 + /// <returns>
7.818 + /// A manipulation event args object.
7.819 + /// </returns>
7.820 + private ManipulationEventArgs CreateManipulationEventArgs(MouseEventArgs e)
7.821 + {
7.822 + return new ManipulationEventArgs(e.Location.ToScreenPoint());
7.823 + }
7.824 +
7.825 + /// <summary>
7.826 + /// Gets the manipulator for the current mouse button and modifier keys.
7.827 + /// </summary>
7.828 + /// <param name="e">
7.829 + /// The event args.
7.830 + /// </param>
7.831 + /// <returns>
7.832 + /// A manipulator or null if no gesture was recognized.
7.833 + /// </returns>
7.834 + private ManipulatorBase GetManipulator(MouseEventArgs e)
7.835 + {
7.836 + bool control = (ModifierKeys & Keys.Control) == Keys.Control;
7.837 + bool shift = (ModifierKeys & Keys.Shift) == Keys.Shift;
7.838 + bool alt = (ModifierKeys & Keys.Alt) == Keys.Alt;
7.839 +
7.840 + bool lmb = e.Button == MouseButtons.Left;
7.841 + bool rmb = e.Button == MouseButtons.Right;
7.842 + bool mmb = e.Button == MouseButtons.Middle;
7.843 + bool xb1 = e.Button == MouseButtons.XButton1;
7.844 + bool xb2 = e.Button == MouseButtons.XButton2;
7.845 +
7.846 + // MMB / control RMB / control+alt LMB
7.847 + if (mmb || (control && rmb) || (control && alt && lmb))
7.848 + {
7.849 + if (e.Clicks == 2)
7.850 + {
7.851 + return new ResetManipulator(this);
7.852 + }
7.853 +
7.854 + return new ZoomRectangleManipulator(this);
7.855 + }
7.856 +
7.857 + // Right mouse button / alt+left mouse button
7.858 + if (rmb || (lmb && alt))
7.859 + {
7.860 + return new PanManipulator(this);
7.861 + }
7.862 +
7.863 + // Left mouse button
7.864 + if (lmb)
7.865 + {
7.866 + return new TrackerManipulator(this) { Snap = !control, PointsOnly = shift };
7.867 + }
7.868 +
7.869 + // XButtons are zoom-stepping
7.870 + if (xb1 || xb2)
7.871 + {
7.872 + double d = xb1 ? 0.05 : -0.05;
7.873 + return new ZoomStepManipulator(this, d, control);
7.874 + }
7.875 +
7.876 + return null;
7.877 + }
7.878 +
7.879 + /// <summary>
7.880 + /// The set clipboard text.
7.881 + /// </summary>
7.882 + /// <param name="text">
7.883 + /// The text.
7.884 + /// </param>
7.885 + private void SetClipboardText(string text)
7.886 + {
7.887 + try
7.888 + {
7.889 + // todo: can't get the following solution to work
7.890 + // http://stackoverflow.com/questions/5707990/requested-clipboard-operation-did-not-succeed
7.891 + Clipboard.SetText(text);
7.892 + }
7.893 + catch (ExternalException ee)
7.894 + {
7.895 + // Requested Clipboard operation did not succeed.
7.896 + MessageBox.Show(this, ee.Message, "OxyPlot");
7.897 + }
7.898 + }
7.899 + }
7.900 +}
7.901 \ No newline at end of file
8.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
8.2 +++ b/External/OxyPlot/OxyPlot.WindowsForms/PlotControl.cs Sat Jun 08 16:53:22 2013 +0000
8.3 @@ -0,0 +1,237 @@
8.4 +// --------------------------------------------------------------------------------------------------------------------
8.5 +// <copyright file="PlotControl.cs" company="OxyPlot">
8.6 +// The MIT License (MIT)
8.7 +//
8.8 +// Copyright (c) 2012 Oystein Bjorke
8.9 +//
8.10 +// Permission is hereby granted, free of charge, to any person obtaining a
8.11 +// copy of this software and associated documentation files (the
8.12 +// "Software"), to deal in the Software without restriction, including
8.13 +// without limitation the rights to use, copy, modify, merge, publish,
8.14 +// distribute, sublicense, and/or sell copies of the Software, and to
8.15 +// permit persons to whom the Software is furnished to do so, subject to
8.16 +// the following conditions:
8.17 +//
8.18 +// The above copyright notice and this permission notice shall be included
8.19 +// in all copies or substantial portions of the Software.
8.20 +//
8.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
8.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
8.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
8.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
8.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
8.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
8.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
8.28 +// </copyright>
8.29 +// --------------------------------------------------------------------------------------------------------------------
8.30 +using System;
8.31 +using System.Collections.Generic;
8.32 +using System.ComponentModel;
8.33 +using System.Drawing;
8.34 +using System.Windows.Forms;
8.35 +using OxyPlot;
8.36 +
8.37 +namespace Oxyplot.WindowsForms
8.38 +{
8.39 + public class PlotControl : Control, IPlotControl
8.40 + {
8.41 + public List<MouseAction> MouseActions { get; private set; }
8.42 +
8.43 + private readonly PanAction panAction;
8.44 + private readonly SliderAction sliderAction;
8.45 + private readonly ZoomAction zoomAction;
8.46 + private Rectangle zoomRectangle;
8.47 +
8.48 + public PlotControl()
8.49 + {
8.50 + // InitializeComponent();
8.51 + DoubleBuffered = true;
8.52 + Model = new PlotModel();
8.53 +
8.54 + panAction = new PanAction(this);
8.55 + zoomAction = new ZoomAction(this);
8.56 + sliderAction = new SliderAction(this);
8.57 +
8.58 + MouseActions = new List<MouseAction>();
8.59 + MouseActions.Add(panAction);
8.60 + MouseActions.Add(zoomAction);
8.61 + MouseActions.Add(sliderAction);
8.62 + }
8.63 +
8.64 + private PlotModel model;
8.65 +
8.66 + [Browsable(false), DefaultValue(null)]
8.67 + public PlotModel Model
8.68 + {
8.69 + get { return model; }
8.70 + set
8.71 + {
8.72 + model = value;
8.73 + Refresh();
8.74 + }
8.75 + }
8.76 +
8.77 + public override void Refresh()
8.78 + {
8.79 + if (model != null)
8.80 + model.UpdateData();
8.81 + base.Refresh();
8.82 + }
8.83 +
8.84 + protected override void OnResize(EventArgs e)
8.85 + {
8.86 + base.OnResize(e);
8.87 + Invalidate();
8.88 + }
8.89 +
8.90 + protected override void OnPaint(PaintEventArgs e)
8.91 + {
8.92 + base.OnPaint(e);
8.93 +
8.94 + var rc = new GraphicsRenderContext(this, e.Graphics, e.ClipRectangle);
8.95 + if (model != null)
8.96 + model.Render(rc);
8.97 + if (zoomRectangle != Rectangle.Empty)
8.98 + {
8.99 + using (var zoomBrush = new SolidBrush(Color.FromArgb(0x40, 0xFF, 0xFF, 0x00)))
8.100 + using (var zoomPen = new Pen(Color.Black))
8.101 + {
8.102 + zoomPen.DashPattern = new float[] { 3, 1 };
8.103 + e.Graphics.FillRectangle(zoomBrush, zoomRectangle);
8.104 + e.Graphics.DrawRectangle(zoomPen, zoomRectangle);
8.105 + }
8.106 + }
8.107 + }
8.108 +
8.109 + protected override void OnKeyDown(KeyEventArgs e)
8.110 + {
8.111 + base.OnKeyDown(e);
8.112 + if (e.KeyCode == Keys.A)
8.113 + {
8.114 + ZoomAll();
8.115 + }
8.116 + }
8.117 +
8.118 + public void ZoomAll()
8.119 + {
8.120 + foreach (var a in Model.Axes)
8.121 + a.Reset();
8.122 + Refresh();
8.123 + }
8.124 +
8.125 + protected override void OnMouseDown(MouseEventArgs e)
8.126 + {
8.127 + base.OnMouseDown(e);
8.128 +
8.129 + Focus();
8.130 + Capture = true;
8.131 +
8.132 + bool control = Control.ModifierKeys == Keys.Control;
8.133 + bool shift = Control.ModifierKeys == Keys.Shift;
8.134 +
8.135 + var button = OxyMouseButton.Left;
8.136 + if (e.Button == MouseButtons.Middle)
8.137 + button = OxyMouseButton.Middle;
8.138 + if (e.Button == MouseButtons.Right)
8.139 + button = OxyMouseButton.Right;
8.140 + if (e.Button == MouseButtons.XButton1)
8.141 + button = OxyMouseButton.XButton1;
8.142 + if (e.Button == MouseButtons.XButton2)
8.143 + button = OxyMouseButton.XButton2;
8.144 +
8.145 + var p = new ScreenPoint(e.X, e.Y);
8.146 + foreach (var a in MouseActions)
8.147 + a.OnMouseDown(p, button, e.Clicks, control, shift);
8.148 + }
8.149 +
8.150 + protected override void OnMouseMove(MouseEventArgs e)
8.151 + {
8.152 + base.OnMouseMove(e);
8.153 + bool control = Control.ModifierKeys == Keys.Control;
8.154 + bool shift = Control.ModifierKeys == Keys.Shift;
8.155 + var p = new ScreenPoint(e.X, e.Y);
8.156 + foreach (var a in MouseActions)
8.157 + a.OnMouseMove(p, control, shift);
8.158 + }
8.159 +
8.160 + protected override void OnMouseUp(MouseEventArgs e)
8.161 + {
8.162 + base.OnMouseUp(e);
8.163 + foreach (var a in MouseActions)
8.164 + a.OnMouseUp();
8.165 + Capture = false;
8.166 + }
8.167 +
8.168 + protected override void OnMouseWheel(MouseEventArgs e)
8.169 + {
8.170 + base.OnMouseWheel(e);
8.171 + bool control = Control.ModifierKeys == Keys.Control;
8.172 + bool shift = Control.ModifierKeys == Keys.Shift;
8.173 + var p = new ScreenPoint(e.X, e.Y);
8.174 + foreach (var a in MouseActions)
8.175 + a.OnMouseWheel(p, e.Delta, control, shift);
8.176 + }
8.177 +
8.178 + public void GetAxesFromPoint(ScreenPoint pt, out AxisBase xaxis, out AxisBase yaxis)
8.179 + {
8.180 + Model.GetAxesFromPoint(pt, out xaxis, out yaxis);
8.181 + }
8.182 +
8.183 + public DataSeries GetSeriesFromPoint(ScreenPoint pt, double limit)
8.184 + {
8.185 + return Model.GetSeriesFromPoint(pt, limit);
8.186 + }
8.187 +
8.188 + public void Refresh(bool refreshData)
8.189 + {
8.190 + if (refreshData)
8.191 + Model.UpdateData();
8.192 + Invalidate();
8.193 + }
8.194 +
8.195 + public void Pan(AxisBase axis, double dx)
8.196 + {
8.197 + axis.Pan(dx);
8.198 + }
8.199 +
8.200 + public void Reset(AxisBase axis)
8.201 + {
8.202 + axis.Reset();
8.203 + }
8.204 +
8.205 + public void Zoom(AxisBase axis, double p1, double p2)
8.206 + {
8.207 + axis.Zoom(p1, p2);
8.208 + }
8.209 +
8.210 + public void ZoomAt(AxisBase axis, double factor, double x)
8.211 + {
8.212 + axis.ZoomAt(factor, x);
8.213 + }
8.214 +
8.215 + public OxyRect GetPlotArea()
8.216 + {
8.217 + return Model.PlotArea;
8.218 + }
8.219 +
8.220 + public void ShowSlider(DataSeries s, DataPoint dp)
8.221 + {
8.222 + }
8.223 +
8.224 + public void HideSlider()
8.225 + {
8.226 + }
8.227 +
8.228 + public void ShowZoomRectangle(OxyRect r)
8.229 + {
8.230 + zoomRectangle = new Rectangle((int)r.Left, (int)r.Top, (int)r.Width, (int)r.Height);
8.231 + Invalidate();
8.232 + }
8.233 +
8.234 + public void HideZoomRectangle()
8.235 + {
8.236 + zoomRectangle = Rectangle.Empty;
8.237 + Invalidate();
8.238 + }
8.239 + }
8.240 +}
8.241 \ No newline at end of file
9.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
9.2 +++ b/External/OxyPlot/OxyPlot.WindowsForms/PngExporter.cs Sat Jun 08 16:53:22 2013 +0000
9.3 @@ -0,0 +1,81 @@
9.4 +// --------------------------------------------------------------------------------------------------------------------
9.5 +// <copyright file="PngExporter.cs" company="OxyPlot">
9.6 +// The MIT License (MIT)
9.7 +//
9.8 +// Copyright (c) 2012 Oystein Bjorke
9.9 +//
9.10 +// Permission is hereby granted, free of charge, to any person obtaining a
9.11 +// copy of this software and associated documentation files (the
9.12 +// "Software"), to deal in the Software without restriction, including
9.13 +// without limitation the rights to use, copy, modify, merge, publish,
9.14 +// distribute, sublicense, and/or sell copies of the Software, and to
9.15 +// permit persons to whom the Software is furnished to do so, subject to
9.16 +// the following conditions:
9.17 +//
9.18 +// The above copyright notice and this permission notice shall be included
9.19 +// in all copies or substantial portions of the Software.
9.20 +//
9.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
9.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
9.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
9.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
9.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
9.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
9.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
9.28 +// </copyright>
9.29 +// <summary>
9.30 +// The png exporter.
9.31 +// </summary>
9.32 +// --------------------------------------------------------------------------------------------------------------------
9.33 +namespace OxyPlot.WindowsForms
9.34 +{
9.35 + using System.Drawing;
9.36 + using System.Drawing.Imaging;
9.37 +
9.38 + using OxyPlot.WindowsForms;
9.39 +
9.40 + /// <summary>
9.41 + /// The png exporter.
9.42 + /// </summary>
9.43 + public static class PngExporter
9.44 + {
9.45 + /// <summary>
9.46 + /// The export.
9.47 + /// </summary>
9.48 + /// <param name="model">
9.49 + /// The model.
9.50 + /// </param>
9.51 + /// <param name="fileName">
9.52 + /// The file name.
9.53 + /// </param>
9.54 + /// <param name="width">
9.55 + /// The width.
9.56 + /// </param>
9.57 + /// <param name="height">
9.58 + /// The height.
9.59 + /// </param>
9.60 + /// <param name="background">
9.61 + /// The background.
9.62 + /// </param>
9.63 + public static void Export(PlotModel model, string fileName, int width, int height, Brush background = null)
9.64 + {
9.65 + using (var bm = new Bitmap(width, height))
9.66 + {
9.67 + using (Graphics g = Graphics.FromImage(bm))
9.68 + {
9.69 + if (background != null)
9.70 + {
9.71 + g.FillRectangle(background, 0, 0, width, height);
9.72 + }
9.73 +
9.74 + var rc = new GraphicsRenderContext { RendersToScreen = false };
9.75 + rc.SetGraphicsTarget(g);
9.76 + model.Update();
9.77 + model.Render(rc, width, height);
9.78 + bm.Save(fileName, ImageFormat.Png);
9.79 + }
9.80 + }
9.81 + }
9.82 +
9.83 + }
9.84 +}
9.85 \ No newline at end of file
10.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
10.2 +++ b/External/OxyPlot/OxyPlot.WindowsForms/Properties/AssemblyInfo.cs Sat Jun 08 16:53:22 2013 +0000
10.3 @@ -0,0 +1,10 @@
10.4 +//-----------------------------------------------------------------------
10.5 +// <copyright file="AssemblyInfo.cs" company="OxyPlot">
10.6 +// http://oxyplot.codeplex.com, license: MIT
10.7 +// </copyright>
10.8 +//-----------------------------------------------------------------------
10.9 +
10.10 +using System.Reflection;
10.11 +
10.12 +[assembly: AssemblyTitle("OxyPlot for Windows Forms")]
10.13 +[assembly: AssemblyDescription("OxyPlot controls for Windows Forms.")]
10.14 \ No newline at end of file
11.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
11.2 +++ b/External/OxyPlot/OxyPlot.sln Sat Jun 08 16:53:22 2013 +0000
11.3 @@ -0,0 +1,26 @@
11.4 +
11.5 +Microsoft Visual Studio Solution File, Format Version 11.00
11.6 +# Visual Studio 2010
11.7 +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "OxyPlot", "OxyPlot\OxyPlot.csproj", "{BCC43E58-E473-403E-A84D-63FEDC723040}"
11.8 +EndProject
11.9 +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "OxyPlot.WindowsForms", "OxyPlot.WindowsForms\OxyPlot.WindowsForms.csproj", "{D4554296-094E-4CAC-8EAE-44EB250666C6}"
11.10 +EndProject
11.11 +Global
11.12 + GlobalSection(SolutionConfigurationPlatforms) = preSolution
11.13 + Debug|Any CPU = Debug|Any CPU
11.14 + Release|Any CPU = Release|Any CPU
11.15 + EndGlobalSection
11.16 + GlobalSection(ProjectConfigurationPlatforms) = postSolution
11.17 + {BCC43E58-E473-403E-A84D-63FEDC723040}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
11.18 + {BCC43E58-E473-403E-A84D-63FEDC723040}.Debug|Any CPU.Build.0 = Debug|Any CPU
11.19 + {BCC43E58-E473-403E-A84D-63FEDC723040}.Release|Any CPU.ActiveCfg = Release|Any CPU
11.20 + {BCC43E58-E473-403E-A84D-63FEDC723040}.Release|Any CPU.Build.0 = Release|Any CPU
11.21 + {D4554296-094E-4CAC-8EAE-44EB250666C6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
11.22 + {D4554296-094E-4CAC-8EAE-44EB250666C6}.Debug|Any CPU.Build.0 = Debug|Any CPU
11.23 + {D4554296-094E-4CAC-8EAE-44EB250666C6}.Release|Any CPU.ActiveCfg = Release|Any CPU
11.24 + {D4554296-094E-4CAC-8EAE-44EB250666C6}.Release|Any CPU.Build.0 = Release|Any CPU
11.25 + EndGlobalSection
11.26 + GlobalSection(SolutionProperties) = preSolution
11.27 + HideSolutionNode = FALSE
11.28 + EndGlobalSection
11.29 +EndGlobal
12.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
12.2 +++ b/External/OxyPlot/OxyPlot/Annotations/Annotation.cs Sat Jun 08 16:53:22 2013 +0000
12.3 @@ -0,0 +1,181 @@
12.4 +// --------------------------------------------------------------------------------------------------------------------
12.5 +// <copyright file="Annotation.cs" company="OxyPlot">
12.6 +// The MIT License (MIT)
12.7 +//
12.8 +// Copyright (c) 2012 Oystein Bjorke
12.9 +//
12.10 +// Permission is hereby granted, free of charge, to any person obtaining a
12.11 +// copy of this software and associated documentation files (the
12.12 +// "Software"), to deal in the Software without restriction, including
12.13 +// without limitation the rights to use, copy, modify, merge, publish,
12.14 +// distribute, sublicense, and/or sell copies of the Software, and to
12.15 +// permit persons to whom the Software is furnished to do so, subject to
12.16 +// the following conditions:
12.17 +//
12.18 +// The above copyright notice and this permission notice shall be included
12.19 +// in all copies or substantial portions of the Software.
12.20 +//
12.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
12.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
12.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
12.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
12.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
12.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
12.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
12.28 +// </copyright>
12.29 +// <summary>
12.30 +// Annotation base class.
12.31 +// </summary>
12.32 +// --------------------------------------------------------------------------------------------------------------------
12.33 +namespace OxyPlot.Annotations
12.34 +{
12.35 + using System;
12.36 + using System.Globalization;
12.37 +
12.38 + using OxyPlot.Axes;
12.39 +
12.40 + /// <summary>
12.41 + /// Provides an abstract base class for annotations.
12.42 + /// </summary>
12.43 + public abstract class Annotation : UIPlotElement
12.44 + {
12.45 + /// <summary>
12.46 + /// Gets the actual culture.
12.47 + /// </summary>
12.48 + /// <remarks>
12.49 + /// The culture is defined in the parent PlotModel.
12.50 + /// </remarks>
12.51 + public CultureInfo ActualCulture
12.52 + {
12.53 + get
12.54 + {
12.55 + return this.PlotModel != null ? this.PlotModel.ActualCulture : CultureInfo.CurrentCulture;
12.56 + }
12.57 + }
12.58 +
12.59 + /// <summary>
12.60 + /// Gets or sets the layer.
12.61 + /// </summary>
12.62 + public AnnotationLayer Layer { get; set; }
12.63 +
12.64 + /// <summary>
12.65 + /// Gets or sets the X axis.
12.66 + /// </summary>
12.67 + /// <value>The X axis.</value>
12.68 + public Axis XAxis { get; set; }
12.69 +
12.70 + /// <summary>
12.71 + /// Gets or sets the X axis key.
12.72 + /// </summary>
12.73 + /// <value>The X axis key.</value>
12.74 + public string XAxisKey { get; set; }
12.75 +
12.76 + /// <summary>
12.77 + /// Gets or sets the Y axis.
12.78 + /// </summary>
12.79 + /// <value>The Y axis.</value>
12.80 + public Axis YAxis { get; set; }
12.81 +
12.82 + /// <summary>
12.83 + /// Gets or sets the Y axis key.
12.84 + /// </summary>
12.85 + /// <value>The Y axis key.</value>
12.86 + public string YAxisKey { get; set; }
12.87 +
12.88 + /// <summary>
12.89 + /// Ensures that the annotation axes are set.
12.90 + /// </summary>
12.91 + public void EnsureAxes()
12.92 + {
12.93 + this.XAxis = this.PlotModel.GetAxisOrDefault(this.XAxisKey, this.PlotModel.DefaultXAxis);
12.94 + this.YAxis = this.PlotModel.GetAxisOrDefault(this.YAxisKey, this.PlotModel.DefaultYAxis);
12.95 + }
12.96 +
12.97 + /// <summary>
12.98 + /// Renders the annotation on the specified context.
12.99 + /// </summary>
12.100 + /// <param name="rc">
12.101 + /// The render context.
12.102 + /// </param>
12.103 + /// <param name="model">
12.104 + /// The model.
12.105 + /// </param>
12.106 + public virtual void Render(IRenderContext rc, PlotModel model)
12.107 + {
12.108 + }
12.109 +
12.110 + /// <summary>
12.111 + /// Tests if the plot element is hit by the specified point.
12.112 + /// </summary>
12.113 + /// <param name="point">The point.</param>
12.114 + /// <param name="tolerance">The tolerance.</param>
12.115 + /// <returns>
12.116 + /// A hit test result.
12.117 + /// </returns>
12.118 + protected internal override HitTestResult HitTest(ScreenPoint point, double tolerance)
12.119 + {
12.120 + return null;
12.121 + }
12.122 +
12.123 + /// <summary>
12.124 + /// Transforms the specified coordinates to a screen point.
12.125 + /// </summary>
12.126 + /// <param name="x">
12.127 + /// The x coordinate.
12.128 + /// </param>
12.129 + /// <param name="y">
12.130 + /// The y coordinate.
12.131 + /// </param>
12.132 + /// <returns>
12.133 + /// A screen point.
12.134 + /// </returns>
12.135 + public ScreenPoint Transform(double x, double y)
12.136 + {
12.137 + return this.XAxis.Transform(x, y, this.YAxis);
12.138 + }
12.139 +
12.140 + /// <summary>
12.141 + /// Transforms the specified data point to a screen point.
12.142 + /// </summary>
12.143 + /// <param name="p">
12.144 + /// The point.
12.145 + /// </param>
12.146 + /// <returns>
12.147 + /// A screen point.
12.148 + /// </returns>
12.149 + public ScreenPoint Transform(IDataPoint p)
12.150 + {
12.151 + return this.XAxis.Transform(p.X, p.Y, this.YAxis);
12.152 + }
12.153 +
12.154 + /// <summary>
12.155 + /// Transforms the specified screen position to a data point.
12.156 + /// </summary>
12.157 + /// <param name="position">
12.158 + /// The position.
12.159 + /// </param>
12.160 + /// <returns>
12.161 + /// A data point
12.162 + /// </returns>
12.163 + public DataPoint InverseTransform(ScreenPoint position)
12.164 + {
12.165 + return Axis.InverseTransform(position, this.XAxis, this.YAxis);
12.166 + }
12.167 +
12.168 + /// <summary>
12.169 + /// Gets the clipping rectangle.
12.170 + /// </summary>
12.171 + /// <returns>
12.172 + /// The clipping rectangle.
12.173 + /// </returns>
12.174 + protected OxyRect GetClippingRect()
12.175 + {
12.176 + double minX = Math.Min(this.XAxis.ScreenMin.X, this.XAxis.ScreenMax.X);
12.177 + double minY = Math.Min(this.YAxis.ScreenMin.Y, this.YAxis.ScreenMax.Y);
12.178 + double maxX = Math.Max(this.XAxis.ScreenMin.X, this.XAxis.ScreenMax.X);
12.179 + double maxY = Math.Max(this.YAxis.ScreenMin.Y, this.YAxis.ScreenMax.Y);
12.180 +
12.181 + return new OxyRect(minX, minY, maxX - minX, maxY - minY);
12.182 + }
12.183 + }
12.184 +}
12.185 \ No newline at end of file
13.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
13.2 +++ b/External/OxyPlot/OxyPlot/Annotations/AnnotationLayer.cs Sat Jun 08 16:53:22 2013 +0000
13.3 @@ -0,0 +1,52 @@
13.4 +// --------------------------------------------------------------------------------------------------------------------
13.5 +// <copyright file="AnnotationLayer.cs" company="OxyPlot">
13.6 +// The MIT License (MIT)
13.7 +//
13.8 +// Copyright (c) 2012 Oystein Bjorke
13.9 +//
13.10 +// Permission is hereby granted, free of charge, to any person obtaining a
13.11 +// copy of this software and associated documentation files (the
13.12 +// "Software"), to deal in the Software without restriction, including
13.13 +// without limitation the rights to use, copy, modify, merge, publish,
13.14 +// distribute, sublicense, and/or sell copies of the Software, and to
13.15 +// permit persons to whom the Software is furnished to do so, subject to
13.16 +// the following conditions:
13.17 +//
13.18 +// The above copyright notice and this permission notice shall be included
13.19 +// in all copies or substantial portions of the Software.
13.20 +//
13.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
13.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
13.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
13.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
13.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
13.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
13.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
13.28 +// </copyright>
13.29 +// <summary>
13.30 +// The annotation layer.
13.31 +// </summary>
13.32 +// --------------------------------------------------------------------------------------------------------------------
13.33 +namespace OxyPlot.Annotations
13.34 +{
13.35 + /// <summary>
13.36 + /// Specifies the layer for an <see cref="Annotation"/>.
13.37 + /// </summary>
13.38 + public enum AnnotationLayer
13.39 + {
13.40 + /// <summary>
13.41 + /// Render the annotation below the gridlines of the axes.
13.42 + /// </summary>
13.43 + BelowAxes,
13.44 +
13.45 + /// <summary>
13.46 + /// Render the annotation below the series.
13.47 + /// </summary>
13.48 + BelowSeries,
13.49 +
13.50 + /// <summary>
13.51 + /// Render the annotation above the series.
13.52 + /// </summary>
13.53 + AboveSeries
13.54 + }
13.55 +}
13.56 \ No newline at end of file
14.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
14.2 +++ b/External/OxyPlot/OxyPlot/Annotations/ArrowAnnotation.cs Sat Jun 08 16:53:22 2013 +0000
14.3 @@ -0,0 +1,228 @@
14.4 +// --------------------------------------------------------------------------------------------------------------------
14.5 +// <copyright file="ArrowAnnotation.cs" company="OxyPlot">
14.6 +// The MIT License (MIT)
14.7 +//
14.8 +// Copyright (c) 2012 Oystein Bjorke
14.9 +//
14.10 +// Permission is hereby granted, free of charge, to any person obtaining a
14.11 +// copy of this software and associated documentation files (the
14.12 +// "Software"), to deal in the Software without restriction, including
14.13 +// without limitation the rights to use, copy, modify, merge, publish,
14.14 +// distribute, sublicense, and/or sell copies of the Software, and to
14.15 +// permit persons to whom the Software is furnished to do so, subject to
14.16 +// the following conditions:
14.17 +//
14.18 +// The above copyright notice and this permission notice shall be included
14.19 +// in all copies or substantial portions of the Software.
14.20 +//
14.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
14.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
14.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
14.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
14.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
14.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
14.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
14.28 +// </copyright>
14.29 +// <summary>
14.30 +// Represents an arrow annotation.
14.31 +// </summary>
14.32 +// --------------------------------------------------------------------------------------------------------------------
14.33 +namespace OxyPlot.Annotations
14.34 +{
14.35 + /// <summary>
14.36 + /// Represents an arrow annotation.
14.37 + /// </summary>
14.38 + public class ArrowAnnotation : TextualAnnotation
14.39 + {
14.40 + /// <summary>
14.41 + /// The end point in screen coordinates.
14.42 + /// </summary>
14.43 + private ScreenPoint screenEndPoint;
14.44 +
14.45 + /// <summary>
14.46 + /// The start point in screen coordinates.
14.47 + /// </summary>
14.48 + private ScreenPoint screenStartPoint;
14.49 +
14.50 + /// <summary>
14.51 + /// Initializes a new instance of the <see cref="ArrowAnnotation"/> class.
14.52 + /// </summary>
14.53 + public ArrowAnnotation()
14.54 + {
14.55 + this.HeadLength = 10;
14.56 + this.HeadWidth = 3;
14.57 + this.Color = OxyColors.Blue;
14.58 + this.StrokeThickness = 2;
14.59 + this.LineStyle = LineStyle.Solid;
14.60 + this.LineJoin = OxyPenLineJoin.Miter;
14.61 + }
14.62 +
14.63 + /// <summary>
14.64 + /// Gets or sets the arrow direction.
14.65 + /// </summary>
14.66 + /// <remarks>
14.67 + /// Setting this property overrides the StartPoint property.
14.68 + /// </remarks>
14.69 + public ScreenVector ArrowDirection { get; set; }
14.70 +
14.71 + /// <summary>
14.72 + /// Gets or sets the color of the arrow.
14.73 + /// </summary>
14.74 + public OxyColor Color { get; set; }
14.75 +
14.76 + /// <summary>
14.77 + /// Gets or sets the end point.
14.78 + /// </summary>
14.79 + public DataPoint EndPoint { get; set; }
14.80 +
14.81 + /// <summary>
14.82 + /// Gets or sets the length of the head (relative to the stroke thickness) (the default value is 10).
14.83 + /// </summary>
14.84 + /// <value> The length of the head. </value>
14.85 + public double HeadLength { get; set; }
14.86 +
14.87 + /// <summary>
14.88 + /// Gets or sets the width of the head (relative to the stroke thickness) (the default value is 3).
14.89 + /// </summary>
14.90 + /// <value> The width of the head. </value>
14.91 + public double HeadWidth { get; set; }
14.92 +
14.93 + /// <summary>
14.94 + /// Gets or sets the line join type.
14.95 + /// </summary>
14.96 + /// <value> The line join type. </value>
14.97 + public OxyPenLineJoin LineJoin { get; set; }
14.98 +
14.99 + /// <summary>
14.100 + /// Gets or sets the line style.
14.101 + /// </summary>
14.102 + /// <value> The line style. </value>
14.103 + public LineStyle LineStyle { get; set; }
14.104 +
14.105 + /// <summary>
14.106 + /// Gets or sets the start point.
14.107 + /// </summary>
14.108 + /// <remarks>
14.109 + /// This property is overridden by the ArrowDirection property, if set.
14.110 + /// </remarks>
14.111 + public DataPoint StartPoint { get; set; }
14.112 +
14.113 + /// <summary>
14.114 + /// Gets or sets the stroke thickness (the default value is 2).
14.115 + /// </summary>
14.116 + /// <value> The stroke thickness. </value>
14.117 + public double StrokeThickness { get; set; }
14.118 +
14.119 + /// <summary>
14.120 + /// Gets or sets the 'veeness' of the arrow head (relative to thickness) (the default value is 0).
14.121 + /// </summary>
14.122 + /// <value> The 'veeness'. </value>
14.123 + public double Veeness { get; set; }
14.124 +
14.125 + /// <summary>
14.126 + /// Renders the arrow annotation.
14.127 + /// </summary>
14.128 + /// <param name="rc">
14.129 + /// The render context.
14.130 + /// </param>
14.131 + /// <param name="model">
14.132 + /// The plot model.
14.133 + /// </param>
14.134 + public override void Render(IRenderContext rc, PlotModel model)
14.135 + {
14.136 + base.Render(rc, model);
14.137 +
14.138 + this.screenEndPoint = this.Transform(this.EndPoint);
14.139 +
14.140 + if (!this.ArrowDirection.x.IsZero() || !this.ArrowDirection.y.IsZero())
14.141 + {
14.142 + this.screenStartPoint = this.screenEndPoint - this.ArrowDirection;
14.143 + }
14.144 + else
14.145 + {
14.146 + this.screenStartPoint = this.Transform(this.StartPoint);
14.147 + }
14.148 +
14.149 + var d = this.screenEndPoint - this.screenStartPoint;
14.150 + d.Normalize();
14.151 + var n = new ScreenVector(d.Y, -d.X);
14.152 +
14.153 + var p1 = this.screenEndPoint - (d * this.HeadLength * this.StrokeThickness);
14.154 + var p2 = p1 + (n * this.HeadWidth * this.StrokeThickness);
14.155 + var p3 = p1 - (n * this.HeadWidth * this.StrokeThickness);
14.156 + var p4 = p1 + (d * this.Veeness * this.StrokeThickness);
14.157 +
14.158 + OxyRect clippingRect = this.GetClippingRect();
14.159 + const double MinimumSegmentLength = 4;
14.160 +
14.161 + rc.DrawClippedLine(
14.162 + new[] { this.screenStartPoint, p4 },
14.163 + clippingRect,
14.164 + MinimumSegmentLength * MinimumSegmentLength,
14.165 + this.GetSelectableColor(this.Color),
14.166 + this.StrokeThickness,
14.167 + this.LineStyle,
14.168 + this.LineJoin,
14.169 + false);
14.170 +
14.171 + rc.DrawClippedPolygon(
14.172 + new[] { p3, this.screenEndPoint, p2, p4 },
14.173 + clippingRect,
14.174 + MinimumSegmentLength * MinimumSegmentLength,
14.175 + this.GetSelectableColor(this.Color),
14.176 + null);
14.177 +
14.178 + if (!string.IsNullOrEmpty(this.Text))
14.179 + {
14.180 + var ha = d.X < 0 ? HorizontalAlignment.Left : HorizontalAlignment.Right;
14.181 + var va = d.Y < 0 ? VerticalAlignment.Top : VerticalAlignment.Bottom;
14.182 +
14.183 + var textPoint = this.screenStartPoint;
14.184 + rc.DrawClippedText(
14.185 + clippingRect,
14.186 + textPoint,
14.187 + this.Text,
14.188 + this.ActualTextColor,
14.189 + this.ActualFont,
14.190 + this.ActualFontSize,
14.191 + this.ActualFontWeight,
14.192 + 0,
14.193 + ha,
14.194 + va);
14.195 + }
14.196 + }
14.197 +
14.198 + /// <summary>
14.199 + /// Tests if the plot element is hit by the specified point.
14.200 + /// </summary>
14.201 + /// <param name="point">
14.202 + /// The point.
14.203 + /// </param>
14.204 + /// <param name="tolerance">
14.205 + /// The tolerance.
14.206 + /// </param>
14.207 + /// <returns>
14.208 + /// A hit test result.
14.209 + /// </returns>
14.210 + protected internal override HitTestResult HitTest(ScreenPoint point, double tolerance)
14.211 + {
14.212 + if ((point - this.screenStartPoint).Length < tolerance)
14.213 + {
14.214 + return new HitTestResult(this.screenStartPoint, null, 1);
14.215 + }
14.216 +
14.217 + if ((point - this.screenEndPoint).Length < tolerance)
14.218 + {
14.219 + return new HitTestResult(this.screenEndPoint, null, 2);
14.220 + }
14.221 +
14.222 + var p = ScreenPointHelper.FindPointOnLine(point, this.screenStartPoint, this.screenEndPoint);
14.223 + if ((p - point).Length < tolerance)
14.224 + {
14.225 + return new HitTestResult(p);
14.226 + }
14.227 +
14.228 + return null;
14.229 + }
14.230 + }
14.231 +}
14.232 \ No newline at end of file
15.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
15.2 +++ b/External/OxyPlot/OxyPlot/Annotations/EllipseAnnotation.cs Sat Jun 08 16:53:22 2013 +0000
15.3 @@ -0,0 +1,152 @@
15.4 +// --------------------------------------------------------------------------------------------------------------------
15.5 +// <copyright file="RectangleAnnotation.cs" company="OxyPlot">
15.6 +// The MIT License (MIT)
15.7 +//
15.8 +// Copyright (c) 2012 Oystein Bjorke
15.9 +//
15.10 +// Permission is hereby granted, free of charge, to any person obtaining a
15.11 +// copy of this software and associated documentation files (the
15.12 +// "Software"), to deal in the Software without restriction, including
15.13 +// without limitation the rights to use, copy, modify, merge, publish,
15.14 +// distribute, sublicense, and/or sell copies of the Software, and to
15.15 +// permit persons to whom the Software is furnished to do so, subject to
15.16 +// the following conditions:
15.17 +//
15.18 +// The above copyright notice and this permission notice shall be included
15.19 +// in all copies or substantial portions of the Software.
15.20 +//
15.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
15.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
15.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
15.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
15.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
15.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
15.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
15.28 +// </copyright>
15.29 +// <summary>
15.30 +// Represents a rectangle annotation.
15.31 +// </summary>
15.32 +// --------------------------------------------------------------------------------------------------------------------
15.33 +namespace OxyPlot.Annotations
15.34 +{
15.35 + /// <summary>
15.36 + /// Represents an ellipse annotation.
15.37 + /// </summary>
15.38 + public class EllipseAnnotation : TextualAnnotation
15.39 + {
15.40 + /// <summary>
15.41 + /// The rectangle transformed to screen coordinates.
15.42 + /// </summary>
15.43 + private OxyRect screenRectangle;
15.44 +
15.45 + /// <summary>
15.46 + /// Initializes a new instance of the <see cref="EllipseAnnotation"/> class.
15.47 + /// </summary>
15.48 + public EllipseAnnotation()
15.49 + {
15.50 + this.Stroke = OxyColors.Black;
15.51 + this.Fill = OxyColors.LightBlue;
15.52 + }
15.53 +
15.54 + /// <summary>
15.55 + /// Gets or sets the fill color.
15.56 + /// </summary>
15.57 + /// <value> The fill. </value>
15.58 + public OxyColor Fill { get; set; }
15.59 +
15.60 + /// <summary>
15.61 + /// Gets or sets the stroke color.
15.62 + /// </summary>
15.63 + public OxyColor Stroke { get; set; }
15.64 +
15.65 + /// <summary>
15.66 + /// Gets or sets the stroke thickness.
15.67 + /// </summary>
15.68 + public double StrokeThickness { get; set; }
15.69 +
15.70 + /// <summary>
15.71 + /// Gets or sets the x-coordinate of the center.
15.72 + /// </summary>
15.73 + public double X { get; set; }
15.74 +
15.75 + /// <summary>
15.76 + /// Gets or sets the y-coordinate of the center.
15.77 + /// </summary>
15.78 + public double Y { get; set; }
15.79 +
15.80 + /// <summary>
15.81 + /// Gets or sets the width of the ellipse.
15.82 + /// </summary>
15.83 + public double Width { get; set; }
15.84 +
15.85 + /// <summary>
15.86 + /// Gets or sets the height of the ellipse.
15.87 + /// </summary>
15.88 + public double Height { get; set; }
15.89 +
15.90 + /// <summary>
15.91 + /// Gets or sets the text rotation (degrees).
15.92 + /// </summary>
15.93 + /// <value>The text rotation in degrees.</value>
15.94 + public double TextRotation { get; set; }
15.95 +
15.96 + /// <summary>
15.97 + /// Renders the polygon annotation.
15.98 + /// </summary>
15.99 + /// <param name="rc">
15.100 + /// The render context.
15.101 + /// </param>
15.102 + /// <param name="model">
15.103 + /// The plot model.
15.104 + /// </param>
15.105 + public override void Render(IRenderContext rc, PlotModel model)
15.106 + {
15.107 + base.Render(rc, model);
15.108 +
15.109 + this.screenRectangle = OxyRect.Create(this.Transform(this.X - (Width / 2), Y - (Height / 2)), this.Transform(X + (Width / 2), Y + (Height / 2)));
15.110 +
15.111 + // clip to the area defined by the axes
15.112 + var clipping = this.GetClippingRect();
15.113 +
15.114 + rc.DrawClippedEllipse(clipping, this.screenRectangle, this.Fill, this.Stroke, this.StrokeThickness);
15.115 +
15.116 + if (!string.IsNullOrEmpty(this.Text))
15.117 + {
15.118 + var textPosition = this.screenRectangle.Center;
15.119 + rc.DrawClippedText(
15.120 + clipping,
15.121 + textPosition,
15.122 + this.Text,
15.123 + this.ActualTextColor,
15.124 + this.ActualFont,
15.125 + this.ActualFontSize,
15.126 + this.ActualFontWeight,
15.127 + this.TextRotation,
15.128 + HorizontalAlignment.Center,
15.129 + VerticalAlignment.Middle);
15.130 + }
15.131 + }
15.132 +
15.133 + /// <summary>
15.134 + /// Tests if the plot element is hit by the specified point.
15.135 + /// </summary>
15.136 + /// <param name="point">
15.137 + /// The point.
15.138 + /// </param>
15.139 + /// <param name="tolerance">
15.140 + /// The tolerance.
15.141 + /// </param>
15.142 + /// <returns>
15.143 + /// A hit test result.
15.144 + /// </returns>
15.145 + protected internal override HitTestResult HitTest(ScreenPoint point, double tolerance)
15.146 + {
15.147 + if (this.screenRectangle.Contains(point))
15.148 + {
15.149 + return new HitTestResult(point);
15.150 + }
15.151 +
15.152 + return null;
15.153 + }
15.154 + }
15.155 +}
15.156 \ No newline at end of file
16.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
16.2 +++ b/External/OxyPlot/OxyPlot/Annotations/ImageAnnotation.cs Sat Jun 08 16:53:22 2013 +0000
16.3 @@ -0,0 +1,451 @@
16.4 +// --------------------------------------------------------------------------------------------------------------------
16.5 +// <copyright file="ImageAnnotation.cs" company="OxyPlot">
16.6 +// The MIT License (MIT)
16.7 +//
16.8 +// Copyright (c) 2012 Oystein Bjorke
16.9 +//
16.10 +// Permission is hereby granted, free of charge, to any person obtaining a
16.11 +// copy of this software and associated documentation files (the
16.12 +// "Software"), to deal in the Software without restriction, including
16.13 +// without limitation the rights to use, copy, modify, merge, publish,
16.14 +// distribute, sublicense, and/or sell copies of the Software, and to
16.15 +// permit persons to whom the Software is furnished to do so, subject to
16.16 +// the following conditions:
16.17 +//
16.18 +// The above copyright notice and this permission notice shall be included
16.19 +// in all copies or substantial portions of the Software.
16.20 +//
16.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
16.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
16.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
16.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
16.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
16.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
16.28 +// </copyright>
16.29 +// <summary>
16.30 +// Represents a text object annotation.
16.31 +// </summary>
16.32 +// --------------------------------------------------------------------------------------------------------------------
16.33 +namespace OxyPlot.Annotations
16.34 +{
16.35 + /// <summary>
16.36 + /// Represents a text annotation.
16.37 + /// </summary>
16.38 + public class ImageAnnotation : Annotation
16.39 + {
16.40 + /// <summary>
16.41 + /// The actual bounds of the rendered image.
16.42 + /// </summary>
16.43 + private OxyRect actualBounds;
16.44 +
16.45 + /// <summary>
16.46 + /// Initializes a new instance of the <see cref="ImageAnnotation" /> class.
16.47 + /// </summary>
16.48 + public ImageAnnotation()
16.49 + {
16.50 + this.X = new PlotLength(0.5, PlotLengthUnit.RelativeToPlotArea);
16.51 + this.Y = new PlotLength(0.5, PlotLengthUnit.RelativeToPlotArea);
16.52 + this.OffsetX = new PlotLength(0, PlotLengthUnit.ScreenUnits);
16.53 + this.OffsetY = new PlotLength(0, PlotLengthUnit.ScreenUnits);
16.54 + this.Width = new PlotLength(double.NaN, PlotLengthUnit.ScreenUnits);
16.55 + this.Height = new PlotLength(double.NaN, PlotLengthUnit.ScreenUnits);
16.56 + this.Opacity = 1.0;
16.57 + this.Interpolate = true;
16.58 + this.HorizontalAlignment = OxyPlot.HorizontalAlignment.Center;
16.59 + this.VerticalAlignment = OxyPlot.VerticalAlignment.Middle;
16.60 + }
16.61 +
16.62 + /// <summary>
16.63 + /// Initializes a new instance of the <see cref="ImageAnnotation"/> class.
16.64 + /// </summary>
16.65 + /// <param name="image">
16.66 + /// The image.
16.67 + /// </param>
16.68 + /// <param name="position">
16.69 + /// The position in screen coordinates.
16.70 + /// </param>
16.71 + /// <param name="horizontalAlignment">
16.72 + /// The horizontal alignment.
16.73 + /// </param>
16.74 + /// <param name="verticalAlignment">
16.75 + /// The vertical alignment.
16.76 + /// </param>
16.77 + public ImageAnnotation(
16.78 + OxyImage image,
16.79 + ScreenPoint position,
16.80 + HorizontalAlignment horizontalAlignment = OxyPlot.HorizontalAlignment.Center,
16.81 + VerticalAlignment verticalAlignment = OxyPlot.VerticalAlignment.Middle)
16.82 + : this()
16.83 + {
16.84 + this.ImageSource = image;
16.85 + this.X = new PlotLength(position.X, PlotLengthUnit.ScreenUnits);
16.86 + this.Y = new PlotLength(position.Y, PlotLengthUnit.ScreenUnits);
16.87 + this.HorizontalAlignment = horizontalAlignment;
16.88 + this.VerticalAlignment = verticalAlignment;
16.89 + }
16.90 +
16.91 + /// <summary>
16.92 + /// Initializes a new instance of the <see cref="ImageAnnotation"/> class.
16.93 + /// </summary>
16.94 + /// <param name="image">
16.95 + /// The image.
16.96 + /// </param>
16.97 + /// <param name="position">
16.98 + /// The position in data coordinates.
16.99 + /// </param>
16.100 + /// <param name="horizontalAlignment">
16.101 + /// The horizontal alignment.
16.102 + /// </param>
16.103 + /// <param name="verticalAlignment">
16.104 + /// The vertical alignment.
16.105 + /// </param>
16.106 + public ImageAnnotation(
16.107 + OxyImage image,
16.108 + IDataPoint position,
16.109 + HorizontalAlignment horizontalAlignment = OxyPlot.HorizontalAlignment.Center,
16.110 + VerticalAlignment verticalAlignment = OxyPlot.VerticalAlignment.Middle)
16.111 + : this()
16.112 + {
16.113 + this.ImageSource = image;
16.114 + this.X = new PlotLength(position.X, PlotLengthUnit.Data);
16.115 + this.Y = new PlotLength(position.Y, PlotLengthUnit.Data);
16.116 + this.HorizontalAlignment = horizontalAlignment;
16.117 + this.VerticalAlignment = verticalAlignment;
16.118 + }
16.119 +
16.120 + /// <summary>
16.121 + /// Initializes a new instance of the <see cref="ImageAnnotation"/> class.
16.122 + /// </summary>
16.123 + /// <param name="image">
16.124 + /// The image.
16.125 + /// </param>
16.126 + /// <param name="relativeX">
16.127 + /// The x-coordinate relative to the plot area (0-1).
16.128 + /// </param>
16.129 + /// <param name="relativeY">
16.130 + /// The y-coordinate relative to the plot area (0-1).
16.131 + /// </param>
16.132 + /// <param name="horizontalAlignment">
16.133 + /// The horizontal alignment.
16.134 + /// </param>
16.135 + /// <param name="verticalAlignment">
16.136 + /// The vertical alignment.
16.137 + /// </param>
16.138 + public ImageAnnotation(
16.139 + OxyImage image,
16.140 + double relativeX,
16.141 + double relativeY,
16.142 + HorizontalAlignment horizontalAlignment = OxyPlot.HorizontalAlignment.Center,
16.143 + VerticalAlignment verticalAlignment = OxyPlot.VerticalAlignment.Middle)
16.144 + : this()
16.145 + {
16.146 + this.ImageSource = image;
16.147 + this.X = new PlotLength(relativeX, PlotLengthUnit.RelativeToPlotArea);
16.148 + this.Y = new PlotLength(relativeY, PlotLengthUnit.RelativeToPlotArea);
16.149 + this.HorizontalAlignment = horizontalAlignment;
16.150 + this.VerticalAlignment = verticalAlignment;
16.151 + }
16.152 +
16.153 + /// <summary>
16.154 + /// Gets or sets the image source.
16.155 + /// </summary>
16.156 + /// <value>
16.157 + /// The image source.
16.158 + /// </value>
16.159 + public OxyImage ImageSource { get; set; }
16.160 +
16.161 + /// <summary>
16.162 + /// Gets or sets the horizontal alignment.
16.163 + /// </summary>
16.164 + /// <value> The horizontal alignment. </value>
16.165 + public HorizontalAlignment HorizontalAlignment { get; set; }
16.166 +
16.167 + /// <summary>
16.168 + /// Gets or sets the X position of the image.
16.169 + /// </summary>
16.170 + /// <value>
16.171 + /// The X.
16.172 + /// </value>
16.173 + public PlotLength X { get; set; }
16.174 +
16.175 + /// <summary>
16.176 + /// Gets or sets the Y position of the image.
16.177 + /// </summary>
16.178 + /// <value>
16.179 + /// The Y.
16.180 + /// </value>
16.181 + public PlotLength Y { get; set; }
16.182 +
16.183 + /// <summary>
16.184 + /// Gets or sets the X offset.
16.185 + /// </summary>
16.186 + /// <value>
16.187 + /// The offset X.
16.188 + /// </value>
16.189 + public PlotLength OffsetX { get; set; }
16.190 +
16.191 + /// <summary>
16.192 + /// Gets or sets the Y offset.
16.193 + /// </summary>
16.194 + /// <value>
16.195 + /// The offset Y.
16.196 + /// </value>
16.197 + public PlotLength OffsetY { get; set; }
16.198 +
16.199 + /// <summary>
16.200 + /// Gets or sets the width.
16.201 + /// </summary>
16.202 + /// <value>
16.203 + /// The width.
16.204 + /// </value>
16.205 + public PlotLength Width { get; set; }
16.206 +
16.207 + /// <summary>
16.208 + /// Gets or sets the height.
16.209 + /// </summary>
16.210 + /// <value>
16.211 + /// The height.
16.212 + /// </value>
16.213 + public PlotLength Height { get; set; }
16.214 +
16.215 + /// <summary>
16.216 + /// Gets or sets the opacity (0-1).
16.217 + /// </summary>
16.218 + /// <value>
16.219 + /// The opacity value.
16.220 + /// </value>
16.221 + public double Opacity { get; set; }
16.222 +
16.223 + /// <summary>
16.224 + /// Gets or sets a value indicating whether to apply smooth interpolation to the image.
16.225 + /// </summary>
16.226 + /// <value>
16.227 + /// <c>true</c> if the image should be interpolated (using a high-quality bi-cubic interpolation); <c>false</c> if the nearest neighbor should be used.
16.228 + /// </value>
16.229 + public bool Interpolate { get; set; }
16.230 +
16.231 + /// <summary>
16.232 + /// Gets or sets the vertical alignment.
16.233 + /// </summary>
16.234 + /// <value> The vertical alignment. </value>
16.235 + public VerticalAlignment VerticalAlignment { get; set; }
16.236 +
16.237 + /// <summary>
16.238 + /// Renders the image annotation.
16.239 + /// </summary>
16.240 + /// <param name="rc">
16.241 + /// The render context.
16.242 + /// </param>
16.243 + /// <param name="model">
16.244 + /// The plot model.
16.245 + /// </param>
16.246 + public override void Render(IRenderContext rc, PlotModel model)
16.247 + {
16.248 + base.Render(rc, model);
16.249 +
16.250 + var p = this.GetPoint(this.X, this.Y, rc, model);
16.251 + var o = this.GetVector(this.OffsetX, this.OffsetY, rc, model);
16.252 + var position = p + o;
16.253 +
16.254 + var clippingRect = this.GetClippingRect();
16.255 +
16.256 + var imageInfo = rc.GetImageInfo(this.ImageSource);
16.257 + if (imageInfo == null)
16.258 + {
16.259 + return;
16.260 + }
16.261 +
16.262 + var s = this.GetVector(this.Width, this.Height, rc, model);
16.263 +
16.264 + var width = s.X;
16.265 + var height = s.Y;
16.266 +
16.267 + if (double.IsNaN(width) && double.IsNaN(height))
16.268 + {
16.269 + width = imageInfo.Width;
16.270 + height = imageInfo.Height;
16.271 + }
16.272 +
16.273 + if (double.IsNaN(width))
16.274 + {
16.275 + width = height / imageInfo.Height * imageInfo.Width;
16.276 + }
16.277 +
16.278 + if (double.IsNaN(height))
16.279 + {
16.280 + height = width / imageInfo.Width * imageInfo.Height;
16.281 + }
16.282 +
16.283 + double x = position.X;
16.284 + double y = position.Y;
16.285 +
16.286 + if (this.HorizontalAlignment == HorizontalAlignment.Center)
16.287 + {
16.288 + x -= width * 0.5;
16.289 + }
16.290 +
16.291 + if (this.HorizontalAlignment == HorizontalAlignment.Right)
16.292 + {
16.293 + x -= width;
16.294 + }
16.295 +
16.296 + if (this.VerticalAlignment == VerticalAlignment.Middle)
16.297 + {
16.298 + y -= height * 0.5;
16.299 + }
16.300 +
16.301 + if (this.VerticalAlignment == VerticalAlignment.Bottom)
16.302 + {
16.303 + y -= height;
16.304 + }
16.305 +
16.306 + this.actualBounds = new OxyRect(x, y, width, height);
16.307 +
16.308 + if (this.X.Unit == PlotLengthUnit.Data || this.Y.Unit == PlotLengthUnit.Data)
16.309 + {
16.310 + rc.DrawClippedImage(clippingRect, this.ImageSource, x, y, width, height, this.Opacity, this.Interpolate);
16.311 + }
16.312 + else
16.313 + {
16.314 + rc.DrawImage(this.ImageSource, x, y, width, height, this.Opacity, this.Interpolate);
16.315 + }
16.316 + }
16.317 +
16.318 + /// <summary>
16.319 + /// Tests if the plot element is hit by the specified point.
16.320 + /// </summary>
16.321 + /// <param name="point">
16.322 + /// The point.
16.323 + /// </param>
16.324 + /// <param name="tolerance">
16.325 + /// The tolerance.
16.326 + /// </param>
16.327 + /// <returns>
16.328 + /// A hit test result.
16.329 + /// </returns>
16.330 + protected internal override HitTestResult HitTest(ScreenPoint point, double tolerance)
16.331 + {
16.332 + if (this.actualBounds.Contains(point))
16.333 + {
16.334 + return new HitTestResult(point);
16.335 + }
16.336 +
16.337 + return null;
16.338 + }
16.339 +
16.340 + /// <summary>
16.341 + /// Gets the point.
16.342 + /// </summary>
16.343 + /// <param name="x">
16.344 + /// The x.
16.345 + /// </param>
16.346 + /// <param name="y">
16.347 + /// The y.
16.348 + /// </param>
16.349 + /// <param name="rc">
16.350 + /// The render context.
16.351 + /// </param>
16.352 + /// <param name="model">
16.353 + /// The model.
16.354 + /// </param>
16.355 + /// <returns>
16.356 + /// The point in screen coordinates.
16.357 + /// </returns>
16.358 + protected ScreenPoint GetPoint(PlotLength x, PlotLength y, IRenderContext rc, PlotModel model)
16.359 + {
16.360 + if (x.Unit == PlotLengthUnit.Data || y.Unit == PlotLengthUnit.Data)
16.361 + {
16.362 + return this.XAxis.Transform(x.Value, y.Value, this.YAxis);
16.363 + }
16.364 +
16.365 + double sx;
16.366 + double sy;
16.367 + switch (x.Unit)
16.368 + {
16.369 + case PlotLengthUnit.RelativeToPlotArea:
16.370 + sx = model.PlotArea.Left + (model.PlotArea.Width * x.Value);
16.371 + break;
16.372 + case PlotLengthUnit.RelativeToViewport:
16.373 + sx = model.Width * x.Value;
16.374 + break;
16.375 + default:
16.376 + sx = x.Value;
16.377 + break;
16.378 + }
16.379 +
16.380 + switch (y.Unit)
16.381 + {
16.382 + case PlotLengthUnit.RelativeToPlotArea:
16.383 + sy = model.PlotArea.Top + (model.PlotArea.Height * y.Value);
16.384 + break;
16.385 + case PlotLengthUnit.RelativeToViewport:
16.386 + sy = model.Height * y.Value;
16.387 + break;
16.388 + default:
16.389 + sy = y.Value;
16.390 + break;
16.391 + }
16.392 +
16.393 + return new ScreenPoint(sx, sy);
16.394 + }
16.395 +
16.396 + /// <summary>
16.397 + /// Gets the vector.
16.398 + /// </summary>
16.399 + /// <param name="x">
16.400 + /// The x component.
16.401 + /// </param>
16.402 + /// <param name="y">
16.403 + /// The y component.
16.404 + /// </param>
16.405 + /// <param name="rc">
16.406 + /// The render context.
16.407 + /// </param>
16.408 + /// <param name="model">
16.409 + /// The model.
16.410 + /// </param>
16.411 + /// <returns>
16.412 + /// The vector in screen coordinates.
16.413 + /// </returns>
16.414 + protected ScreenVector GetVector(PlotLength x, PlotLength y, IRenderContext rc, PlotModel model)
16.415 + {
16.416 + double sx;
16.417 + double sy;
16.418 +
16.419 + switch (x.Unit)
16.420 + {
16.421 + case PlotLengthUnit.Data:
16.422 + sx = this.XAxis.Transform(x.Value) - this.XAxis.Transform(0);
16.423 + break;
16.424 + case PlotLengthUnit.RelativeToPlotArea:
16.425 + sx = model.PlotArea.Width * x.Value;
16.426 + break;
16.427 + case PlotLengthUnit.RelativeToViewport:
16.428 + sx = model.Width * x.Value;
16.429 + break;
16.430 + default:
16.431 + sx = x.Value;
16.432 + break;
16.433 + }
16.434 +
16.435 + switch (y.Unit)
16.436 + {
16.437 + case PlotLengthUnit.Data:
16.438 + sy = this.YAxis.Transform(y.Value) - this.YAxis.Transform(0);
16.439 + break;
16.440 + case PlotLengthUnit.RelativeToPlotArea:
16.441 + sy = model.PlotArea.Height * y.Value;
16.442 + break;
16.443 + case PlotLengthUnit.RelativeToViewport:
16.444 + sy = model.Height * y.Value;
16.445 + break;
16.446 + default:
16.447 + sy = y.Value;
16.448 + break;
16.449 + }
16.450 +
16.451 + return new ScreenVector(sx, sy);
16.452 + }
16.453 + }
16.454 +}
16.455 \ No newline at end of file
17.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
17.2 +++ b/External/OxyPlot/OxyPlot/Annotations/LineAnnotation.cs Sat Jun 08 16:53:22 2013 +0000
17.3 @@ -0,0 +1,528 @@
17.4 +// --------------------------------------------------------------------------------------------------------------------
17.5 +// <copyright file="LineAnnotation.cs" company="OxyPlot">
17.6 +// The MIT License (MIT)
17.7 +//
17.8 +// Copyright (c) 2012 Oystein Bjorke
17.9 +//
17.10 +// Permission is hereby granted, free of charge, to any person obtaining a
17.11 +// copy of this software and associated documentation files (the
17.12 +// "Software"), to deal in the Software without restriction, including
17.13 +// without limitation the rights to use, copy, modify, merge, publish,
17.14 +// distribute, sublicense, and/or sell copies of the Software, and to
17.15 +// permit persons to whom the Software is furnished to do so, subject to
17.16 +// the following conditions:
17.17 +//
17.18 +// The above copyright notice and this permission notice shall be included
17.19 +// in all copies or substantial portions of the Software.
17.20 +//
17.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
17.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
17.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
17.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
17.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
17.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
17.28 +// </copyright>
17.29 +// <summary>
17.30 +// Specify the orientation of the annotation text
17.31 +// </summary>
17.32 +// --------------------------------------------------------------------------------------------------------------------
17.33 +namespace OxyPlot.Annotations
17.34 +{
17.35 + using System;
17.36 + using System.Collections.Generic;
17.37 + using System.Linq;
17.38 +
17.39 + using OxyPlot.Axes;
17.40 +
17.41 + /// <summary>
17.42 + /// Specifes the orientation of the annotation text
17.43 + /// </summary>
17.44 + public enum AnnotationTextOrientation
17.45 + {
17.46 + /// <summary>
17.47 + /// Horizontal text.
17.48 + /// </summary>
17.49 + Horizontal,
17.50 +
17.51 + /// <summary>
17.52 + /// Vertical text.
17.53 + /// </summary>
17.54 + Vertical,
17.55 +
17.56 + /// <summary>
17.57 + /// Oriented along the line.
17.58 + /// </summary>
17.59 + AlongLine
17.60 + }
17.61 +
17.62 + /// <summary>
17.63 + /// Represents a line annotation.
17.64 + /// </summary>
17.65 + public class LineAnnotation : TextualAnnotation
17.66 + {
17.67 + /// <summary>
17.68 + /// The points of the line, transformed to screen coordinates.
17.69 + /// </summary>
17.70 + private IList<ScreenPoint> screenPoints;
17.71 +
17.72 + /// <summary>
17.73 + /// Initializes a new instance of the <see cref = "LineAnnotation" /> class.
17.74 + /// </summary>
17.75 + public LineAnnotation()
17.76 + {
17.77 + this.Type = LineAnnotationType.LinearEquation;
17.78 + this.MinimumX = double.MinValue;
17.79 + this.MaximumX = double.MaxValue;
17.80 + this.MinimumY = double.MinValue;
17.81 + this.MaximumY = double.MaxValue;
17.82 + this.Color = OxyColors.Blue;
17.83 + this.StrokeThickness = 1;
17.84 + this.LineStyle = LineStyle.Dash;
17.85 + this.LineJoin = OxyPenLineJoin.Miter;
17.86 + this.ClipByXAxis = true;
17.87 + this.ClipByYAxis = true;
17.88 +
17.89 + this.TextPosition = 1;
17.90 + this.TextOrientation = AnnotationTextOrientation.AlongLine;
17.91 + this.TextMargin = 12;
17.92 + this.TextHorizontalAlignment = HorizontalAlignment.Right;
17.93 + this.TextVerticalAlignment = VerticalAlignment.Top;
17.94 + }
17.95 +
17.96 + /// <summary>
17.97 + /// Gets or sets the color of the line.
17.98 + /// </summary>
17.99 + public OxyColor Color { get; set; }
17.100 +
17.101 + /// <summary>
17.102 + /// Gets or sets the y=f(x) equation when Type is Equation.
17.103 + /// </summary>
17.104 + public Func<double, double> Equation { get; set; }
17.105 +
17.106 + /// <summary>
17.107 + /// Gets or sets the y-intercept when Type is LinearEquation.
17.108 + /// </summary>
17.109 + /// <value>The intercept value.</value>
17.110 + /// <remarks>
17.111 + /// Linear equation y-intercept (the b in y=mx+b).
17.112 + /// http://en.wikipedia.org/wiki/Linear_equation
17.113 + /// </remarks>
17.114 + public double Intercept { get; set; }
17.115 +
17.116 + /// <summary>
17.117 + /// Gets or sets the line join.
17.118 + /// </summary>
17.119 + /// <value>The line join.</value>
17.120 + public OxyPenLineJoin LineJoin { get; set; }
17.121 +
17.122 + /// <summary>
17.123 + /// Gets or sets the line style.
17.124 + /// </summary>
17.125 + /// <value>The line style.</value>
17.126 + public LineStyle LineStyle { get; set; }
17.127 +
17.128 + /// <summary>
17.129 + /// Gets or sets the maximum X coordinate for the line.
17.130 + /// </summary>
17.131 + public double MaximumX { get; set; }
17.132 +
17.133 + /// <summary>
17.134 + /// Gets or sets the maximum Y coordinate for the line.
17.135 + /// </summary>
17.136 + public double MaximumY { get; set; }
17.137 +
17.138 + /// <summary>
17.139 + /// Gets or sets the minimum X coordinate for the line.
17.140 + /// </summary>
17.141 + public double MinimumX { get; set; }
17.142 +
17.143 + /// <summary>
17.144 + /// Gets or sets the minimum Y coordinate for the line.
17.145 + /// </summary>
17.146 + public double MinimumY { get; set; }
17.147 +
17.148 + /// <summary>
17.149 + /// Gets or sets the slope when Type is LinearEquation.
17.150 + /// </summary>
17.151 + /// <value>The slope value.</value>
17.152 + /// <remarks>
17.153 + /// Linear equation slope (the m in y=mx+b)
17.154 + /// http://en.wikipedia.org/wiki/Linear_equation
17.155 + /// </remarks>
17.156 + public double Slope { get; set; }
17.157 +
17.158 + /// <summary>
17.159 + /// Gets or sets the stroke thickness.
17.160 + /// </summary>
17.161 + /// <value>The stroke thickness.</value>
17.162 + public double StrokeThickness { get; set; }
17.163 +
17.164 + /// <summary>
17.165 + /// Gets or sets the text horizontal alignment.
17.166 + /// </summary>
17.167 + /// <value>The text horizontal alignment.</value>
17.168 + public HorizontalAlignment TextHorizontalAlignment { get; set; }
17.169 +
17.170 + /// <summary>
17.171 + /// Gets or sets the text margin (along the line).
17.172 + /// </summary>
17.173 + /// <value>The text margin.</value>
17.174 + public double TextMargin { get; set; }
17.175 +
17.176 + /// <summary>
17.177 + /// Gets or sets the text padding (in the direction of the text).
17.178 + /// </summary>
17.179 + /// <value>The text padding.</value>
17.180 + public double TextPadding { get; set; }
17.181 +
17.182 + /// <summary>
17.183 + /// Gets or sets the text orientation.
17.184 + /// </summary>
17.185 + /// <value>The text orientation.</value>
17.186 + public AnnotationTextOrientation TextOrientation { get; set; }
17.187 +
17.188 + /// <summary>
17.189 + /// Gets or sets the text position fraction.
17.190 + /// </summary>
17.191 + /// <value>The text position in the interval [0,1].</value>
17.192 + /// <remarks>
17.193 + /// Positions smaller than 0.25 are left aligned at the start of the line
17.194 + /// Positions larger than 0.75 are right aligned at the end of the line
17.195 + /// Other positions are center aligned at the specified position
17.196 + /// </remarks>
17.197 + public double TextPosition { get; set; }
17.198 +
17.199 + /// <summary>
17.200 + /// Gets or sets the vertical alignment of text (above or below the line).
17.201 + /// </summary>
17.202 + public VerticalAlignment TextVerticalAlignment { get; set; }
17.203 +
17.204 + /// <summary>
17.205 + /// Gets or sets the type of line equation.
17.206 + /// </summary>
17.207 + public LineAnnotationType Type { get; set; }
17.208 +
17.209 + /// <summary>
17.210 + /// Gets or sets the X position for vertical lines (only for Type==Vertical).
17.211 + /// </summary>
17.212 + public double X { get; set; }
17.213 +
17.214 + /// <summary>
17.215 + /// Gets or sets the Y position for horizontal lines (only for Type==Horizontal)
17.216 + /// </summary>
17.217 + public double Y { get; set; }
17.218 +
17.219 + /// <summary>
17.220 + /// Gets or sets a value indicating whether to clip the annotation line by the X axis range.
17.221 + /// </summary>
17.222 + /// <value><c>true</c> if clipping by the X axis is enabled; otherwise, <c>false</c>.</value>
17.223 + public bool ClipByXAxis { get; set; }
17.224 +
17.225 + /// <summary>
17.226 + /// Gets or sets a value indicating whether to clip the annotation line by the Y axis range.
17.227 + /// </summary>
17.228 + /// <value><c>true</c> if clipping by the Y axis is enabled; otherwise, <c>false</c>.</value>
17.229 + public bool ClipByYAxis { get; set; }
17.230 +
17.231 + /// <summary>
17.232 + /// Renders the line annotation.
17.233 + /// </summary>
17.234 + /// <param name="rc">
17.235 + /// The render context.
17.236 + /// </param>
17.237 + /// <param name="model">
17.238 + /// The plot model.
17.239 + /// </param>
17.240 + public override void Render(IRenderContext rc, PlotModel model)
17.241 + {
17.242 + base.Render(rc, model);
17.243 +
17.244 + bool aliased = false;
17.245 +
17.246 + double actualMinimumX = Math.Max(this.MinimumX, this.XAxis.ActualMinimum);
17.247 + double actualMaximumX = Math.Min(this.MaximumX, this.XAxis.ActualMaximum);
17.248 + double actualMinimumY = Math.Max(this.MinimumY, this.YAxis.ActualMinimum);
17.249 + double actualMaximumY = Math.Min(this.MaximumY, this.YAxis.ActualMaximum);
17.250 +
17.251 + if (!this.ClipByXAxis)
17.252 + {
17.253 + double right = XAxis.InverseTransform(PlotModel.PlotArea.Right);
17.254 + double left = XAxis.InverseTransform(PlotModel.PlotArea.Left);
17.255 + actualMaximumX = Math.Max(left, right);
17.256 + actualMinimumX = Math.Min(left, right);
17.257 + }
17.258 +
17.259 + if (!this.ClipByYAxis)
17.260 + {
17.261 + double bottom = YAxis.InverseTransform(PlotModel.PlotArea.Bottom);
17.262 + double top = YAxis.InverseTransform(PlotModel.PlotArea.Top);
17.263 + actualMaximumY = Math.Max(top, bottom);
17.264 + actualMinimumY = Math.Min(top, bottom);
17.265 + }
17.266 +
17.267 + // y=f(x)
17.268 + Func<double, double> fx = null;
17.269 +
17.270 + // x=f(y)
17.271 + Func<double, double> fy = null;
17.272 +
17.273 + switch (this.Type)
17.274 + {
17.275 + case LineAnnotationType.Horizontal:
17.276 + fx = x => this.Y;
17.277 + break;
17.278 + case LineAnnotationType.Vertical:
17.279 + fy = y => this.X;
17.280 + break;
17.281 + case LineAnnotationType.EquationY:
17.282 + fx = this.Equation;
17.283 + break;
17.284 + case LineAnnotationType.EquationX:
17.285 + fy = this.Equation;
17.286 + break;
17.287 + default:
17.288 + fx = x => (this.Slope * x) + this.Intercept;
17.289 + break;
17.290 + }
17.291 +
17.292 + var points = new List<DataPoint>();
17.293 +
17.294 + bool isCurvedLine = !(this.XAxis is LinearAxis) || !(this.YAxis is LinearAxis) || this.Type == LineAnnotationType.EquationY;
17.295 +
17.296 + if (!isCurvedLine)
17.297 + {
17.298 + // we only need to calculate two points if it is a straight line
17.299 + if (fx != null)
17.300 + {
17.301 + points.Add(new DataPoint(actualMinimumX, fx(actualMinimumX)));
17.302 + points.Add(new DataPoint(actualMaximumX, fx(actualMaximumX)));
17.303 + }
17.304 + else if (fy != null)
17.305 + {
17.306 + points.Add(new DataPoint(fy(actualMinimumY), actualMinimumY));
17.307 + points.Add(new DataPoint(fy(actualMaximumY), actualMaximumY));
17.308 + }
17.309 +
17.310 + if (this.Type == LineAnnotationType.Horizontal || this.Type == LineAnnotationType.Vertical)
17.311 + {
17.312 + // use aliased line drawing for horizontal and vertical lines
17.313 + aliased = true;
17.314 + }
17.315 + }
17.316 + else
17.317 + {
17.318 + if (fx != null)
17.319 + {
17.320 + double x = actualMinimumX;
17.321 +
17.322 + // todo: the step size should be adaptive
17.323 + double dx = (actualMaximumX - actualMinimumX) / 100;
17.324 + while (true)
17.325 + {
17.326 + points.Add(new DataPoint(x, fx(x)));
17.327 + if (x > actualMaximumX)
17.328 + {
17.329 + break;
17.330 + }
17.331 +
17.332 + x += dx;
17.333 + }
17.334 + }
17.335 + else if (fy != null)
17.336 + {
17.337 + double y = actualMinimumY;
17.338 +
17.339 + // todo: the step size should be adaptive
17.340 + double dy = (actualMaximumY - actualMinimumY) / 100;
17.341 + while (true)
17.342 + {
17.343 + points.Add(new DataPoint(fy(y), y));
17.344 + if (y > actualMaximumY)
17.345 + {
17.346 + break;
17.347 + }
17.348 +
17.349 + y += dy;
17.350 + }
17.351 + }
17.352 + }
17.353 +
17.354 + // transform to screen coordinates
17.355 + this.screenPoints = points.Select(p => this.Transform(p)).ToList();
17.356 +
17.357 + // clip to the area defined by the axes
17.358 + var clippingRectangle = OxyRect.Create(
17.359 + this.ClipByXAxis ? this.XAxis.ScreenMin.X : PlotModel.PlotArea.Left,
17.360 + this.ClipByYAxis ? this.YAxis.ScreenMin.Y : PlotModel.PlotArea.Top,
17.361 + this.ClipByXAxis ? this.XAxis.ScreenMax.X : PlotModel.PlotArea.Right,
17.362 + this.ClipByYAxis ? this.YAxis.ScreenMax.Y : PlotModel.PlotArea.Bottom);
17.363 +
17.364 + const double MinimumSegmentLength = 4;
17.365 +
17.366 + IList<ScreenPoint> clippedPoints = null;
17.367 +
17.368 + rc.DrawClippedLine(
17.369 + this.screenPoints,
17.370 + clippingRectangle,
17.371 + MinimumSegmentLength * MinimumSegmentLength,
17.372 + this.GetSelectableColor(this.Color),
17.373 + this.StrokeThickness,
17.374 + this.LineStyle,
17.375 + this.LineJoin,
17.376 + aliased,
17.377 + pts => clippedPoints = pts);
17.378 +
17.379 + ScreenPoint position;
17.380 + double angle;
17.381 + double margin = this.TextMargin;
17.382 +
17.383 + if (this.TextHorizontalAlignment == HorizontalAlignment.Center)
17.384 + {
17.385 + margin = 0;
17.386 + }
17.387 + else
17.388 + {
17.389 + margin *= this.TextPosition < 0.5 ? 1 : -1;
17.390 + }
17.391 +
17.392 + if (clippedPoints != null && GetPointAtRelativeDistance(clippedPoints, this.TextPosition, margin, out position, out angle))
17.393 + {
17.394 + if (angle < -90)
17.395 + {
17.396 + angle += 180;
17.397 + }
17.398 +
17.399 + if (angle > 90)
17.400 + {
17.401 + angle -= 180;
17.402 + }
17.403 +
17.404 + switch (this.TextOrientation)
17.405 + {
17.406 + case AnnotationTextOrientation.Horizontal:
17.407 + angle = 0;
17.408 + break;
17.409 + case AnnotationTextOrientation.Vertical:
17.410 + angle = -90;
17.411 + break;
17.412 + }
17.413 +
17.414 + // Apply 'padding' to the position
17.415 + var angleInRadians = angle / 180 * Math.PI;
17.416 + var f = 1;
17.417 +
17.418 + if (this.TextHorizontalAlignment == HorizontalAlignment.Right)
17.419 + {
17.420 + f = -1;
17.421 + }
17.422 +
17.423 + if (this.TextHorizontalAlignment == HorizontalAlignment.Center)
17.424 + {
17.425 + f = 0;
17.426 + }
17.427 +
17.428 + position.X += f * this.TextPadding * Math.Cos(angleInRadians);
17.429 + position.Y += f * this.TextPadding * Math.Sin(angleInRadians);
17.430 +
17.431 + var cs = new CohenSutherlandClipping(clippingRectangle);
17.432 + if (!string.IsNullOrEmpty(this.Text) && cs.IsInside(position))
17.433 + {
17.434 + rc.DrawClippedText(
17.435 + clippingRectangle,
17.436 + position,
17.437 + this.Text,
17.438 + this.ActualTextColor,
17.439 + this.ActualFont,
17.440 + this.ActualFontSize,
17.441 + this.ActualFontWeight,
17.442 + angle,
17.443 + this.TextHorizontalAlignment,
17.444 + this.TextVerticalAlignment);
17.445 + }
17.446 + }
17.447 + }
17.448 +
17.449 + /// <summary>
17.450 + /// Tests if the plot element is hit by the specified point.
17.451 + /// </summary>
17.452 + /// <param name="point">The point.</param>
17.453 + /// <param name="tolerance">The tolerance.</param>
17.454 + /// <returns>
17.455 + /// A hit test result.
17.456 + /// </returns>
17.457 + protected internal override HitTestResult HitTest(ScreenPoint point, double tolerance)
17.458 + {
17.459 + var nearestPoint = ScreenPointHelper.FindNearestPointOnPolyline(point, this.screenPoints);
17.460 + double dist = (point - nearestPoint).Length;
17.461 + if (dist < tolerance)
17.462 + {
17.463 + return new HitTestResult(nearestPoint);
17.464 + }
17.465 +
17.466 + return null;
17.467 + }
17.468 +
17.469 + /// <summary>
17.470 + /// Gets the point on a curve at the specified relative distance along the curve.
17.471 + /// </summary>
17.472 + /// <param name="pts">
17.473 + /// The curve points.
17.474 + /// </param>
17.475 + /// <param name="p">
17.476 + /// The relative distance along the curve.
17.477 + /// </param>
17.478 + /// <param name="margin">
17.479 + /// The margins.
17.480 + /// </param>
17.481 + /// <param name="position">
17.482 + /// The position.
17.483 + /// </param>
17.484 + /// <param name="angle">
17.485 + /// The angle.
17.486 + /// </param>
17.487 + /// <returns>
17.488 + /// True if a position was found.
17.489 + /// </returns>
17.490 + private static bool GetPointAtRelativeDistance(
17.491 + IList<ScreenPoint> pts, double p, double margin, out ScreenPoint position, out double angle)
17.492 + {
17.493 + if (pts == null || pts.Count == 0)
17.494 + {
17.495 + position = new ScreenPoint();
17.496 + angle = 0;
17.497 + return false;
17.498 + }
17.499 +
17.500 + double length = 0;
17.501 + for (int i = 1; i < pts.Count; i++)
17.502 + {
17.503 + length += (pts[i] - pts[i - 1]).Length;
17.504 + }
17.505 +
17.506 + double l = (length * p) + margin;
17.507 + length = 0;
17.508 + for (int i = 1; i < pts.Count; i++)
17.509 + {
17.510 + double dl = (pts[i] - pts[i - 1]).Length;
17.511 + if (l >= length && l <= length + dl)
17.512 + {
17.513 + double f = (l - length) / dl;
17.514 + double x = (pts[i].X * f) + (pts[i - 1].X * (1 - f));
17.515 + double y = (pts[i].Y * f) + (pts[i - 1].Y * (1 - f));
17.516 + position = new ScreenPoint(x, y);
17.517 + double dx = pts[i].X - pts[i - 1].X;
17.518 + double dy = pts[i].Y - pts[i - 1].Y;
17.519 + angle = Math.Atan2(dy, dx) / Math.PI * 180;
17.520 + return true;
17.521 + }
17.522 +
17.523 + length += dl;
17.524 + }
17.525 +
17.526 + position = pts[0];
17.527 + angle = 0;
17.528 + return false;
17.529 + }
17.530 + }
17.531 +}
17.532 \ No newline at end of file
18.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
18.2 +++ b/External/OxyPlot/OxyPlot/Annotations/LineAnnotationType.cs Sat Jun 08 16:53:22 2013 +0000
18.3 @@ -0,0 +1,62 @@
18.4 +// --------------------------------------------------------------------------------------------------------------------
18.5 +// <copyright file="LineAnnotationType.cs" company="OxyPlot">
18.6 +// The MIT License (MIT)
18.7 +//
18.8 +// Copyright (c) 2012 Oystein Bjorke
18.9 +//
18.10 +// Permission is hereby granted, free of charge, to any person obtaining a
18.11 +// copy of this software and associated documentation files (the
18.12 +// "Software"), to deal in the Software without restriction, including
18.13 +// without limitation the rights to use, copy, modify, merge, publish,
18.14 +// distribute, sublicense, and/or sell copies of the Software, and to
18.15 +// permit persons to whom the Software is furnished to do so, subject to
18.16 +// the following conditions:
18.17 +//
18.18 +// The above copyright notice and this permission notice shall be included
18.19 +// in all copies or substantial portions of the Software.
18.20 +//
18.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
18.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
18.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
18.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
18.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
18.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
18.28 +// </copyright>
18.29 +// <summary>
18.30 +// The line annotation type.
18.31 +// </summary>
18.32 +// --------------------------------------------------------------------------------------------------------------------
18.33 +namespace OxyPlot.Annotations
18.34 +{
18.35 + /// <summary>
18.36 + /// Specifies the definition of the line in a <see cref="LineAnnotation"/>.
18.37 + /// </summary>
18.38 + public enum LineAnnotationType
18.39 + {
18.40 + /// <summary>
18.41 + /// Horizontal line given by the Y property
18.42 + /// </summary>
18.43 + Horizontal,
18.44 +
18.45 + /// <summary>
18.46 + /// Vertical line given by the X property
18.47 + /// </summary>
18.48 + Vertical,
18.49 +
18.50 + /// <summary>
18.51 + /// Linear equation y=mx+b given by the Slope and Intercept properties
18.52 + /// </summary>
18.53 + LinearEquation,
18.54 +
18.55 + /// <summary>
18.56 + /// Curve equation x=f(y) given by the Equation property
18.57 + /// </summary>
18.58 + EquationX,
18.59 +
18.60 + /// <summary>
18.61 + /// Curve equation y=f(x) given by the Equation property
18.62 + /// </summary>
18.63 + EquationY
18.64 + }
18.65 +}
18.66 \ No newline at end of file
19.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
19.2 +++ b/External/OxyPlot/OxyPlot/Annotations/PolygonAnnotation.cs Sat Jun 08 16:53:22 2013 +0000
19.3 @@ -0,0 +1,166 @@
19.4 +// --------------------------------------------------------------------------------------------------------------------
19.5 +// <copyright file="PolygonAnnotation.cs" company="OxyPlot">
19.6 +// The MIT License (MIT)
19.7 +//
19.8 +// Copyright (c) 2012 Oystein Bjorke
19.9 +//
19.10 +// Permission is hereby granted, free of charge, to any person obtaining a
19.11 +// copy of this software and associated documentation files (the
19.12 +// "Software"), to deal in the Software without restriction, including
19.13 +// without limitation the rights to use, copy, modify, merge, publish,
19.14 +// distribute, sublicense, and/or sell copies of the Software, and to
19.15 +// permit persons to whom the Software is furnished to do so, subject to
19.16 +// the following conditions:
19.17 +//
19.18 +// The above copyright notice and this permission notice shall be included
19.19 +// in all copies or substantial portions of the Software.
19.20 +//
19.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
19.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
19.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
19.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
19.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
19.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
19.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
19.28 +// </copyright>
19.29 +// <summary>
19.30 +// Represents a polygon annotation.
19.31 +// </summary>
19.32 +// --------------------------------------------------------------------------------------------------------------------
19.33 +namespace OxyPlot.Annotations
19.34 +{
19.35 + using System.Collections.Generic;
19.36 + using System.Linq;
19.37 +
19.38 + /// <summary>
19.39 + /// Represents a polygon annotation.
19.40 + /// </summary>
19.41 + public class PolygonAnnotation : TextualAnnotation
19.42 + {
19.43 + /// <summary>
19.44 + /// The polygon points transformed to screen coordinates.
19.45 + /// </summary>
19.46 + private IList<ScreenPoint> screenPoints;
19.47 +
19.48 + /// <summary>
19.49 + /// Initializes a new instance of the <see cref="PolygonAnnotation"/> class.
19.50 + /// </summary>
19.51 + public PolygonAnnotation()
19.52 + {
19.53 + this.Color = OxyColors.Blue;
19.54 + this.Fill = OxyColors.LightBlue;
19.55 + this.StrokeThickness = 1;
19.56 + this.LineStyle = LineStyle.Solid;
19.57 + this.LineJoin = OxyPenLineJoin.Miter;
19.58 + }
19.59 +
19.60 + /// <summary>
19.61 + /// Gets or sets the color of the line.
19.62 + /// </summary>
19.63 + public OxyColor Color { get; set; }
19.64 +
19.65 + /// <summary>
19.66 + /// Gets or sets the fill color.
19.67 + /// </summary>
19.68 + /// <value> The fill. </value>
19.69 + public OxyColor Fill { get; set; }
19.70 +
19.71 + /// <summary>
19.72 + /// Gets or sets the line join.
19.73 + /// </summary>
19.74 + /// <value> The line join. </value>
19.75 + public OxyPenLineJoin LineJoin { get; set; }
19.76 +
19.77 + /// <summary>
19.78 + /// Gets or sets the line style.
19.79 + /// </summary>
19.80 + /// <value> The line style. </value>
19.81 + public LineStyle LineStyle { get; set; }
19.82 +
19.83 + /// <summary>
19.84 + /// Gets or sets the points.
19.85 + /// </summary>
19.86 + /// <value> The points. </value>
19.87 + public IList<DataPoint> Points { get; set; }
19.88 +
19.89 + /// <summary>
19.90 + /// Gets or sets the stroke thickness.
19.91 + /// </summary>
19.92 + /// <value> The stroke thickness. </value>
19.93 + public double StrokeThickness { get; set; }
19.94 +
19.95 + /// <summary>
19.96 + /// Renders the polygon annotation.
19.97 + /// </summary>
19.98 + /// <param name="rc">
19.99 + /// The render context.
19.100 + /// </param>
19.101 + /// <param name="model">
19.102 + /// The plot model.
19.103 + /// </param>
19.104 + public override void Render(IRenderContext rc, PlotModel model)
19.105 + {
19.106 + base.Render(rc, model);
19.107 + if (this.Points == null)
19.108 + {
19.109 + return;
19.110 + }
19.111 +
19.112 + // transform to screen coordinates
19.113 + this.screenPoints = this.Points.Select(p => this.Transform(p)).ToList();
19.114 + if (this.screenPoints.Count == 0)
19.115 + {
19.116 + return;
19.117 + }
19.118 +
19.119 + // clip to the area defined by the axes
19.120 + var clipping = this.GetClippingRect();
19.121 +
19.122 + const double MinimumSegmentLength = 4;
19.123 +
19.124 + rc.DrawClippedPolygon(
19.125 + this.screenPoints,
19.126 + clipping,
19.127 + MinimumSegmentLength * MinimumSegmentLength,
19.128 + this.GetSelectableFillColor(this.Fill),
19.129 + this.GetSelectableColor(this.Color),
19.130 + this.StrokeThickness,
19.131 + this.LineStyle,
19.132 + this.LineJoin);
19.133 +
19.134 + if (!string.IsNullOrEmpty(this.Text))
19.135 + {
19.136 + var textPosition = ScreenPointHelper.GetCentroid(this.screenPoints);
19.137 +
19.138 + rc.DrawClippedText(
19.139 + clipping,
19.140 + textPosition,
19.141 + this.Text,
19.142 + this.ActualTextColor,
19.143 + this.ActualFont,
19.144 + this.ActualFontSize,
19.145 + this.ActualFontWeight,
19.146 + 0,
19.147 + HorizontalAlignment.Center,
19.148 + VerticalAlignment.Middle);
19.149 + }
19.150 + }
19.151 +
19.152 + /// <summary>
19.153 + /// Tests if the plot element is hit by the specified point.
19.154 + /// </summary>
19.155 + /// <param name="point">
19.156 + /// The point.
19.157 + /// </param>
19.158 + /// <param name="tolerance">
19.159 + /// The tolerance.
19.160 + /// </param>
19.161 + /// <returns>
19.162 + /// A hit test result.
19.163 + /// </returns>
19.164 + protected internal override HitTestResult HitTest(ScreenPoint point, double tolerance)
19.165 + {
19.166 + return ScreenPointHelper.IsPointInPolygon(point, this.screenPoints) ? new HitTestResult(point) : null;
19.167 + }
19.168 + }
19.169 +}
19.170 \ No newline at end of file
20.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
20.2 +++ b/External/OxyPlot/OxyPlot/Annotations/RectangleAnnotation.cs Sat Jun 08 16:53:22 2013 +0000
20.3 @@ -0,0 +1,174 @@
20.4 +// --------------------------------------------------------------------------------------------------------------------
20.5 +// <copyright file="RectangleAnnotation.cs" company="OxyPlot">
20.6 +// The MIT License (MIT)
20.7 +//
20.8 +// Copyright (c) 2012 Oystein Bjorke
20.9 +//
20.10 +// Permission is hereby granted, free of charge, to any person obtaining a
20.11 +// copy of this software and associated documentation files (the
20.12 +// "Software"), to deal in the Software without restriction, including
20.13 +// without limitation the rights to use, copy, modify, merge, publish,
20.14 +// distribute, sublicense, and/or sell copies of the Software, and to
20.15 +// permit persons to whom the Software is furnished to do so, subject to
20.16 +// the following conditions:
20.17 +//
20.18 +// The above copyright notice and this permission notice shall be included
20.19 +// in all copies or substantial portions of the Software.
20.20 +//
20.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
20.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
20.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
20.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
20.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
20.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
20.28 +// </copyright>
20.29 +// <summary>
20.30 +// Represents a rectangle annotation.
20.31 +// </summary>
20.32 +// --------------------------------------------------------------------------------------------------------------------
20.33 +namespace OxyPlot.Annotations
20.34 +{
20.35 + /// <summary>
20.36 + /// Represents a rectangle annotation.
20.37 + /// </summary>
20.38 + public class RectangleAnnotation : TextualAnnotation
20.39 + {
20.40 + /// <summary>
20.41 + /// The rectangle transformed to screen coordinates.
20.42 + /// </summary>
20.43 + private OxyRect screenRectangle;
20.44 +
20.45 + /// <summary>
20.46 + /// Initializes a new instance of the <see cref="RectangleAnnotation"/> class.
20.47 + /// </summary>
20.48 + public RectangleAnnotation()
20.49 + {
20.50 + this.Stroke = OxyColors.Black;
20.51 + this.Fill = OxyColors.LightBlue;
20.52 + this.MinimumX = double.MinValue;
20.53 + this.MaximumX = double.MaxValue;
20.54 + this.MinimumY = double.MinValue;
20.55 + this.MaximumY = double.MaxValue;
20.56 + this.TextRotation = 0;
20.57 + }
20.58 +
20.59 + /// <summary>
20.60 + /// Gets or sets the fill color.
20.61 + /// </summary>
20.62 + /// <value> The fill. </value>
20.63 + public OxyColor Fill { get; set; }
20.64 +
20.65 + /// <summary>
20.66 + /// Gets or sets the stroke color.
20.67 + /// </summary>
20.68 + public OxyColor Stroke { get; set; }
20.69 +
20.70 + /// <summary>
20.71 + /// Gets or sets the stroke thickness.
20.72 + /// </summary>
20.73 + public double StrokeThickness { get; set; }
20.74 +
20.75 + /// <summary>
20.76 + /// Gets or sets the minimum X.
20.77 + /// </summary>
20.78 + /// <value>The minimum X.</value>
20.79 + public double MinimumX { get; set; }
20.80 +
20.81 + /// <summary>
20.82 + /// Gets or sets the maximum X.
20.83 + /// </summary>
20.84 + /// <value>The maximum X.</value>
20.85 + public double MaximumX { get; set; }
20.86 +
20.87 + /// <summary>
20.88 + /// Gets or sets the minimum Y.
20.89 + /// </summary>
20.90 + /// <value>The minimum Y.</value>
20.91 + public double MinimumY { get; set; }
20.92 +
20.93 + /// <summary>
20.94 + /// Gets or sets the maximum Y.
20.95 + /// </summary>
20.96 + /// <value>The maximum Y.</value>
20.97 + public double MaximumY { get; set; }
20.98 +
20.99 + /// <summary>
20.100 + /// Gets or sets the text rotation (degrees).
20.101 + /// </summary>
20.102 + /// <value>The text rotation in degrees.</value>
20.103 + public double TextRotation { get; set; }
20.104 +
20.105 + /// <summary>
20.106 + /// Renders the polygon annotation.
20.107 + /// </summary>
20.108 + /// <param name="rc">
20.109 + /// The render context.
20.110 + /// </param>
20.111 + /// <param name="model">
20.112 + /// The plot model.
20.113 + /// </param>
20.114 + public override void Render(IRenderContext rc, PlotModel model)
20.115 + {
20.116 + base.Render(rc, model);
20.117 +
20.118 + double x0 = double.IsNaN(this.MinimumX) || this.MinimumX.Equals(double.MinValue)
20.119 + ? this.XAxis.ActualMinimum
20.120 + : this.MinimumX;
20.121 + double x1 = double.IsNaN(this.MaximumX) || this.MaximumX.Equals(double.MaxValue)
20.122 + ? this.XAxis.ActualMaximum
20.123 + : this.MaximumX;
20.124 + double y0 = double.IsNaN(this.MinimumY) || this.MinimumY.Equals(double.MinValue)
20.125 + ? this.YAxis.ActualMinimum
20.126 + : this.MinimumY;
20.127 + double y1 = double.IsNaN(this.MaximumY) || this.MaximumY.Equals(double.MaxValue)
20.128 + ? this.YAxis.ActualMaximum
20.129 + : this.MaximumY;
20.130 +
20.131 + this.screenRectangle = OxyRect.Create(this.Transform(x0, y0), this.Transform(x1, y1));
20.132 +
20.133 + // clip to the area defined by the axes
20.134 + var clipping = this.GetClippingRect();
20.135 +
20.136 + rc.DrawClippedRectangle(this.screenRectangle, clipping, this.Fill, this.Stroke, this.StrokeThickness);
20.137 +
20.138 + if (!string.IsNullOrEmpty(this.Text))
20.139 + {
20.140 + var textPosition = this.screenRectangle.Center;
20.141 + rc.DrawClippedText(
20.142 + clipping,
20.143 + textPosition,
20.144 + this.Text,
20.145 + this.ActualTextColor,
20.146 + this.ActualFont,
20.147 + this.ActualFontSize,
20.148 + this.ActualFontWeight,
20.149 + this.TextRotation,
20.150 + HorizontalAlignment.Center,
20.151 + VerticalAlignment.Middle);
20.152 + }
20.153 + }
20.154 +
20.155 + /// <summary>
20.156 + /// Tests if the plot element is hit by the specified point.
20.157 + /// </summary>
20.158 + /// <param name="point">
20.159 + /// The point.
20.160 + /// </param>
20.161 + /// <param name="tolerance">
20.162 + /// The tolerance.
20.163 + /// </param>
20.164 + /// <returns>
20.165 + /// A hit test result.
20.166 + /// </returns>
20.167 + protected internal override HitTestResult HitTest(ScreenPoint point, double tolerance)
20.168 + {
20.169 + if (this.screenRectangle.Contains(point))
20.170 + {
20.171 + return new HitTestResult(point);
20.172 + }
20.173 +
20.174 + return null;
20.175 + }
20.176 + }
20.177 +}
20.178 \ No newline at end of file
21.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
21.2 +++ b/External/OxyPlot/OxyPlot/Annotations/TextAnnotation.cs Sat Jun 08 16:53:22 2013 +0000
21.3 @@ -0,0 +1,254 @@
21.4 +// --------------------------------------------------------------------------------------------------------------------
21.5 +// <copyright file="TextAnnotation.cs" company="OxyPlot">
21.6 +// The MIT License (MIT)
21.7 +//
21.8 +// Copyright (c) 2012 Oystein Bjorke
21.9 +//
21.10 +// Permission is hereby granted, free of charge, to any person obtaining a
21.11 +// copy of this software and associated documentation files (the
21.12 +// "Software"), to deal in the Software without restriction, including
21.13 +// without limitation the rights to use, copy, modify, merge, publish,
21.14 +// distribute, sublicense, and/or sell copies of the Software, and to
21.15 +// permit persons to whom the Software is furnished to do so, subject to
21.16 +// the following conditions:
21.17 +//
21.18 +// The above copyright notice and this permission notice shall be included
21.19 +// in all copies or substantial portions of the Software.
21.20 +//
21.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
21.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
21.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
21.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
21.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
21.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
21.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21.28 +// </copyright>
21.29 +// <summary>
21.30 +// Represents a text object annotation.
21.31 +// </summary>
21.32 +// --------------------------------------------------------------------------------------------------------------------
21.33 +namespace OxyPlot.Annotations
21.34 +{
21.35 + using System;
21.36 + using System.Collections.Generic;
21.37 +
21.38 + /// <summary>
21.39 + /// Represents a text annotation.
21.40 + /// </summary>
21.41 + public class TextAnnotation : TextualAnnotation
21.42 + {
21.43 + /// <summary>
21.44 + /// The actual bounds of the text.
21.45 + /// </summary>
21.46 + private IList<ScreenPoint> actualBounds;
21.47 +
21.48 + /// <summary>
21.49 + /// Initializes a new instance of the <see cref="TextAnnotation" /> class.
21.50 + /// </summary>
21.51 + public TextAnnotation()
21.52 + {
21.53 + this.TextColor = OxyColors.Blue;
21.54 + this.Stroke = OxyColors.Black;
21.55 + this.Background = null;
21.56 + this.StrokeThickness = 1;
21.57 + this.Rotation = 0;
21.58 + this.HorizontalAlignment = OxyPlot.HorizontalAlignment.Center;
21.59 + this.VerticalAlignment = OxyPlot.VerticalAlignment.Bottom;
21.60 + this.Padding = new OxyThickness(4);
21.61 + }
21.62 +
21.63 + /// <summary>
21.64 + /// Gets or sets the fill color of the background rectangle.
21.65 + /// </summary>
21.66 + /// <value> The background. </value>
21.67 + public OxyColor Background { get; set; }
21.68 +
21.69 + /// <summary>
21.70 + /// Gets or sets the horizontal alignment.
21.71 + /// </summary>
21.72 + /// <value> The horizontal alignment. </value>
21.73 + public HorizontalAlignment HorizontalAlignment { get; set; }
21.74 +
21.75 + /// <summary>
21.76 + /// Gets or sets the position offset (screen coordinates).
21.77 + /// </summary>
21.78 + /// <value> The offset. </value>
21.79 + public ScreenVector Offset { get; set; }
21.80 +
21.81 + /// <summary>
21.82 + /// Gets or sets the padding of the background rectangle.
21.83 + /// </summary>
21.84 + /// <value> The padding. </value>
21.85 + public OxyThickness Padding { get; set; }
21.86 +
21.87 + /// <summary>
21.88 + /// Gets or sets the position of the text.
21.89 + /// </summary>
21.90 + public DataPoint Position { get; set; }
21.91 +
21.92 + /// <summary>
21.93 + /// Gets or sets the rotation angle (degrees).
21.94 + /// </summary>
21.95 + /// <value> The rotation. </value>
21.96 + public double Rotation { get; set; }
21.97 +
21.98 + /// <summary>
21.99 + /// Gets or sets the stroke color of the background rectangle.
21.100 + /// </summary>
21.101 + /// <value> The stroke color. </value>
21.102 + public OxyColor Stroke { get; set; }
21.103 +
21.104 + /// <summary>
21.105 + /// Gets or sets the stroke thickness of the background rectangle.
21.106 + /// </summary>
21.107 + /// <value> The stroke thickness. </value>
21.108 + public double StrokeThickness { get; set; }
21.109 +
21.110 + /// <summary>
21.111 + /// Gets or sets the vertical alignment.
21.112 + /// </summary>
21.113 + /// <value> The vertical alignment. </value>
21.114 + public VerticalAlignment VerticalAlignment { get; set; }
21.115 +
21.116 + /// <summary>
21.117 + /// Renders the text annotation.
21.118 + /// </summary>
21.119 + /// <param name="rc">
21.120 + /// The render context.
21.121 + /// </param>
21.122 + /// <param name="model">
21.123 + /// The plot model.
21.124 + /// </param>
21.125 + public override void Render(IRenderContext rc, PlotModel model)
21.126 + {
21.127 + base.Render(rc, model);
21.128 +
21.129 + var position = this.Transform(this.Position);
21.130 + position.X += this.Offset.X;
21.131 + position.Y += this.Offset.Y;
21.132 +
21.133 + var clippingRect = this.GetClippingRect();
21.134 +
21.135 + var textSize = rc.MeasureText(this.Text, this.ActualFont, this.ActualFontSize, this.ActualFontWeight);
21.136 +
21.137 + const double MinDistSquared = 4;
21.138 +
21.139 + this.actualBounds = GetTextBounds(
21.140 + position, textSize, this.Padding, this.Rotation, this.HorizontalAlignment, this.VerticalAlignment);
21.141 + rc.DrawClippedPolygon(
21.142 + this.actualBounds, clippingRect, MinDistSquared, this.Background, this.Stroke, this.StrokeThickness);
21.143 +
21.144 + rc.DrawClippedText(
21.145 + clippingRect,
21.146 + position,
21.147 + this.Text,
21.148 + this.GetSelectableFillColor(this.ActualTextColor),
21.149 + this.ActualFont,
21.150 + this.ActualFontSize,
21.151 + this.ActualFontWeight,
21.152 + this.Rotation,
21.153 + this.HorizontalAlignment,
21.154 + this.VerticalAlignment);
21.155 + }
21.156 +
21.157 + /// <summary>
21.158 + /// Tests if the plot element is hit by the specified point.
21.159 + /// </summary>
21.160 + /// <param name="point">
21.161 + /// The point.
21.162 + /// </param>
21.163 + /// <param name="tolerance">
21.164 + /// The tolerance.
21.165 + /// </param>
21.166 + /// <returns>
21.167 + /// A hit test result.
21.168 + /// </returns>
21.169 + protected internal override HitTestResult HitTest(ScreenPoint point, double tolerance)
21.170 + {
21.171 + if (this.actualBounds == null)
21.172 + {
21.173 + return null;
21.174 + }
21.175 +
21.176 + // Todo: see if performance can be improved by checking rectangle (with rotation and alignment), not polygon
21.177 + return ScreenPointHelper.IsPointInPolygon(point, this.actualBounds) ? new HitTestResult(point) : null;
21.178 + }
21.179 +
21.180 + /// <summary>
21.181 + /// Gets the coordinates of the (rotated) background rectangle.
21.182 + /// </summary>
21.183 + /// <param name="position">
21.184 + /// The position.
21.185 + /// </param>
21.186 + /// <param name="size">
21.187 + /// The size.
21.188 + /// </param>
21.189 + /// <param name="padding">
21.190 + /// The padding.
21.191 + /// </param>
21.192 + /// <param name="rotation">
21.193 + /// The rotation.
21.194 + /// </param>
21.195 + /// <param name="horizontalAlignment">
21.196 + /// The horizontal alignment.
21.197 + /// </param>
21.198 + /// <param name="verticalAlignment">
21.199 + /// The vertical alignment.
21.200 + /// </param>
21.201 + /// <returns>
21.202 + /// The background rectangle coordinates.
21.203 + /// </returns>
21.204 + private static IList<ScreenPoint> GetTextBounds(
21.205 + ScreenPoint position,
21.206 + OxySize size,
21.207 + OxyThickness padding,
21.208 + double rotation,
21.209 + HorizontalAlignment horizontalAlignment,
21.210 + VerticalAlignment verticalAlignment)
21.211 + {
21.212 + double left, right, top, bottom;
21.213 + switch (horizontalAlignment)
21.214 + {
21.215 + case HorizontalAlignment.Center:
21.216 + left = -size.Width * 0.5;
21.217 + right = -left;
21.218 + break;
21.219 + case HorizontalAlignment.Right:
21.220 + left = -size.Width;
21.221 + right = 0;
21.222 + break;
21.223 + default:
21.224 + left = 0;
21.225 + right = size.Width;
21.226 + break;
21.227 + }
21.228 +
21.229 + switch (verticalAlignment)
21.230 + {
21.231 + case VerticalAlignment.Middle:
21.232 + top = -size.Height * 0.5;
21.233 + bottom = -top;
21.234 + break;
21.235 + case VerticalAlignment.Bottom:
21.236 + top = -size.Height;
21.237 + bottom = 0;
21.238 + break;
21.239 + default:
21.240 + top = 0;
21.241 + bottom = size.Height;
21.242 + break;
21.243 + }
21.244 +
21.245 + double cost = Math.Cos(rotation / 180 * Math.PI);
21.246 + double sint = Math.Sin(rotation / 180 * Math.PI);
21.247 + var u = new ScreenVector(cost, sint);
21.248 + var v = new ScreenVector(-sint, cost);
21.249 + var polygon = new ScreenPoint[4];
21.250 + polygon[0] = position + (u * (left - padding.Left)) + (v * (top - padding.Top));
21.251 + polygon[1] = position + (u * (right + padding.Right)) + (v * (top - padding.Top));
21.252 + polygon[2] = position + (u * (right + padding.Right)) + (v * (bottom + padding.Bottom));
21.253 + polygon[3] = position + (u * (left - padding.Left)) + (v * (bottom + padding.Bottom));
21.254 + return polygon;
21.255 + }
21.256 + }
21.257 +}
21.258 \ No newline at end of file
22.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
22.2 +++ b/External/OxyPlot/OxyPlot/Annotations/TextualAnnotation.cs Sat Jun 08 16:53:22 2013 +0000
22.3 @@ -0,0 +1,46 @@
22.4 +// --------------------------------------------------------------------------------------------------------------------
22.5 +// <copyright file="TextualAnnotation.cs" company="OxyPlot">
22.6 +// The MIT License (MIT)
22.7 +//
22.8 +// Copyright (c) 2012 Oystein Bjorke
22.9 +//
22.10 +// Permission is hereby granted, free of charge, to any person obtaining a
22.11 +// copy of this software and associated documentation files (the
22.12 +// "Software"), to deal in the Software without restriction, including
22.13 +// without limitation the rights to use, copy, modify, merge, publish,
22.14 +// distribute, sublicense, and/or sell copies of the Software, and to
22.15 +// permit persons to whom the Software is furnished to do so, subject to
22.16 +// the following conditions:
22.17 +//
22.18 +// The above copyright notice and this permission notice shall be included
22.19 +// in all copies or substantial portions of the Software.
22.20 +//
22.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
22.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
22.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
22.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
22.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
22.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
22.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22.28 +// </copyright>
22.29 +// <summary>
22.30 +// Provides an abstract base class for annotations that contains text.
22.31 +// </summary>
22.32 +// --------------------------------------------------------------------------------------------------------------------
22.33 +
22.34 +namespace OxyPlot.Annotations
22.35 +{
22.36 + /// <summary>
22.37 + /// Provides an abstract base class for annotations that contains text.
22.38 + /// </summary>
22.39 + public abstract class TextualAnnotation : Annotation
22.40 + {
22.41 + /// <summary>
22.42 + /// Gets or sets the annotation text.
22.43 + /// </summary>
22.44 + /// <value>
22.45 + /// The text.
22.46 + /// </value>
22.47 + public string Text { get; set; }
22.48 + }
22.49 +}
22.50 \ No newline at end of file
23.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
23.2 +++ b/External/OxyPlot/OxyPlot/Annotations/TileMapAnnotation.cs Sat Jun 08 16:53:22 2013 +0000
23.3 @@ -0,0 +1,457 @@
23.4 +// --------------------------------------------------------------------------------------------------------------------
23.5 +// <copyright file="TileMapAnnotation.cs" company="OxyPlot">
23.6 +// The MIT License (MIT)
23.7 +//
23.8 +// Copyright (c) 2012 Oystein Bjorke
23.9 +//
23.10 +// Permission is hereby granted, free of charge, to any person obtaining a
23.11 +// copy of this software and associated documentation files (the
23.12 +// "Software"), to deal in the Software without restriction, including
23.13 +// without limitation the rights to use, copy, modify, merge, publish,
23.14 +// distribute, sublicense, and/or sell copies of the Software, and to
23.15 +// permit persons to whom the Software is furnished to do so, subject to
23.16 +// the following conditions:
23.17 +//
23.18 +// The above copyright notice and this permission notice shall be included
23.19 +// in all copies or substantial portions of the Software.
23.20 +//
23.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
23.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
23.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
23.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
23.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
23.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
23.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23.28 +// </copyright>
23.29 +// <summary>
23.30 +// Provides a tile map annotation.
23.31 +// </summary>
23.32 +// --------------------------------------------------------------------------------------------------------------------
23.33 +
23.34 +namespace OxyPlot.Annotations
23.35 +{
23.36 + using System;
23.37 + using System.Collections.Generic;
23.38 + using System.Globalization;
23.39 + using System.IO;
23.40 + using System.Net;
23.41 + using System.Threading;
23.42 +
23.43 + /// <summary>
23.44 + /// Provides a tile map annotation.
23.45 + /// </summary>
23.46 + /// <remarks>
23.47 + /// The longitude and latitude range of the map is defined by the range of the x and y axis, respectively.
23.48 + /// </remarks>
23.49 + public class TileMapAnnotation : Annotation
23.50 + {
23.51 + /// <summary>
23.52 + /// The image cache.
23.53 + /// </summary>
23.54 + private readonly Dictionary<string, OxyImage> images = new Dictionary<string, OxyImage>();
23.55 +
23.56 + /// <summary>
23.57 + /// The download queue.
23.58 + /// </summary>
23.59 + private readonly Queue<string> queue = new Queue<string>();
23.60 +
23.61 + /// <summary>
23.62 + /// The current number of downloads
23.63 + /// </summary>
23.64 + private int numberOfDownloads;
23.65 +
23.66 + /// <summary>
23.67 + /// Initializes a new instance of the <see cref="TileMapAnnotation" /> class.
23.68 + /// </summary>
23.69 + public TileMapAnnotation()
23.70 + {
23.71 + this.TileSize = 256;
23.72 + this.MinZoomLevel = 0;
23.73 + this.MaxZoomLevel = 20;
23.74 + this.Opacity = 1.0;
23.75 + this.MaxNumberOfDownloads = 8;
23.76 + }
23.77 +
23.78 + /// <summary>
23.79 + /// Gets or sets the max number of simultaneous downloads.
23.80 + /// </summary>
23.81 + /// <value>
23.82 + /// The max number of downloads.
23.83 + /// </value>
23.84 + public int MaxNumberOfDownloads { get; set; }
23.85 +
23.86 + /// <summary>
23.87 + /// Gets or sets the URL.
23.88 + /// </summary>
23.89 + /// <value>
23.90 + /// The URL.
23.91 + /// </value>
23.92 + public string Url { get; set; }
23.93 +
23.94 + /// <summary>
23.95 + /// Gets or sets the copyright notice.
23.96 + /// </summary>
23.97 + /// <value>
23.98 + /// The copyright notice.
23.99 + /// </value>
23.100 + public string CopyrightNotice { get; set; }
23.101 +
23.102 + /// <summary>
23.103 + /// Gets or sets the size of the tiles.
23.104 + /// </summary>
23.105 + /// <value>
23.106 + /// The size of the tiles.
23.107 + /// </value>
23.108 + public int TileSize { get; set; }
23.109 +
23.110 + /// <summary>
23.111 + /// Gets or sets the min zoom level.
23.112 + /// </summary>
23.113 + /// <value>
23.114 + /// The min zoom level.
23.115 + /// </value>
23.116 + public int MinZoomLevel { get; set; }
23.117 +
23.118 + /// <summary>
23.119 + /// Gets or sets the max zoom level.
23.120 + /// </summary>
23.121 + /// <value>
23.122 + /// The max zoom level.
23.123 + /// </value>
23.124 + public int MaxZoomLevel { get; set; }
23.125 +
23.126 + /// <summary>
23.127 + /// Gets or sets the opacity.
23.128 + /// </summary>
23.129 + /// <value>
23.130 + /// The opacity.
23.131 + /// </value>
23.132 + public double Opacity { get; set; }
23.133 +
23.134 + /// <summary>
23.135 + /// Renders the annotation on the specified context.
23.136 + /// </summary>
23.137 + /// <param name="rc">
23.138 + /// The render context.
23.139 + /// </param>
23.140 + /// <param name="model">
23.141 + /// The model.
23.142 + /// </param>
23.143 + public override void Render(IRenderContext rc, PlotModel model)
23.144 + {
23.145 + base.Render(rc, model);
23.146 + var clippingRect = this.GetClippingRect();
23.147 + var lon0 = this.XAxis.ActualMinimum;
23.148 + var lon1 = this.XAxis.ActualMaximum;
23.149 + var lat0 = this.YAxis.ActualMinimum;
23.150 + var lat1 = this.YAxis.ActualMaximum;
23.151 +
23.152 + // the desired number of tiles horizontally
23.153 + double tilesx = model.Width / this.TileSize;
23.154 +
23.155 + // calculate the desired zoom level
23.156 + var n = tilesx / (((lon1 + 180) / 360) - ((lon0 + 180) / 360));
23.157 + var zoom = (int)Math.Round(Math.Log(n) / Math.Log(2));
23.158 + if (zoom < this.MinZoomLevel)
23.159 + {
23.160 + zoom = this.MinZoomLevel;
23.161 + }
23.162 +
23.163 + if (zoom > this.MaxZoomLevel)
23.164 + {
23.165 + zoom = this.MaxZoomLevel;
23.166 + }
23.167 +
23.168 + // find tile coordinates for the corners
23.169 + double x0, y0;
23.170 + LatLonToTile(lat0, lon0, zoom, out x0, out y0);
23.171 + double x1, y1;
23.172 + LatLonToTile(lat1, lon1, zoom, out x1, out y1);
23.173 +
23.174 + double xmax = Math.Max(x0, x1);
23.175 + double xmin = Math.Min(x0, x1);
23.176 + double ymax = Math.Max(y0, y1);
23.177 + double ymin = Math.Min(y0, y1);
23.178 +
23.179 + // Add the tiles
23.180 + for (var x = (int)xmin; x < xmax; x++)
23.181 + {
23.182 + for (var y = (int)ymin; y < ymax; y++)
23.183 + {
23.184 + string uri = this.GetTileUri(x, y, zoom);
23.185 + var img = this.GetImage(uri, rc.RendersToScreen);
23.186 +
23.187 + if (img == null)
23.188 + {
23.189 + continue;
23.190 + }
23.191 +
23.192 + // transform from tile coordinates to lat/lon
23.193 + double latitude0, latitude1, longitude0, longitude1;
23.194 + TileToLatLon(x, y, zoom, out latitude0, out longitude0);
23.195 + TileToLatLon(x + 1, y + 1, zoom, out latitude1, out longitude1);
23.196 +
23.197 + // transform from lat/lon to screen coordinates
23.198 + var s00 = this.Transform(longitude0, latitude0);
23.199 + var s11 = this.Transform(longitude1, latitude1);
23.200 +
23.201 + var r = OxyRect.Create(s00.X, s00.Y, s11.X, s11.Y);
23.202 +
23.203 + // draw the image
23.204 + rc.DrawClippedImage(clippingRect, img, r.Left, r.Top, r.Width, r.Height, this.Opacity, true);
23.205 + }
23.206 + }
23.207 +
23.208 + // draw the copyright notice
23.209 + var p = new ScreenPoint(clippingRect.Right - 5, clippingRect.Bottom - 5);
23.210 + var textSize = rc.MeasureText(this.CopyrightNotice, null, 12);
23.211 + rc.DrawRectangle(new OxyRect(p.X - textSize.Width - 2, p.Y - textSize.Height - 2, textSize.Width + 4, textSize.Height + 4), OxyColors.White.ChangeAlpha(200), null);
23.212 +
23.213 + rc.DrawText(
23.214 + p,
23.215 + this.CopyrightNotice,
23.216 + OxyColors.Black,
23.217 + null,
23.218 + 12,
23.219 + 500,
23.220 + 0,
23.221 + HorizontalAlignment.Right,
23.222 + VerticalAlignment.Bottom);
23.223 + }
23.224 +
23.225 + /// <summary>
23.226 + /// Tests if the plot element is hit by the specified point.
23.227 + /// </summary>
23.228 + /// <param name="point">
23.229 + /// The point.
23.230 + /// </param>
23.231 + /// <param name="tolerance">
23.232 + /// The tolerance.
23.233 + /// </param>
23.234 + /// <returns>
23.235 + /// A hit test result.
23.236 + /// </returns>
23.237 + protected internal override HitTestResult HitTest(ScreenPoint point, double tolerance)
23.238 + {
23.239 + return null;
23.240 + }
23.241 +
23.242 + /// <summary>
23.243 + /// Transforms a position to a tile coordinate.
23.244 + /// </summary>
23.245 + /// <param name="latitude">The latitude.</param>
23.246 + /// <param name="longitude">The longitude.</param>
23.247 + /// <param name="zoom">The zoom.</param>
23.248 + /// <param name="x">The x.</param>
23.249 + /// <param name="y">The y.</param>
23.250 + private static void LatLonToTile(double latitude, double longitude, int zoom, out double x, out double y)
23.251 + {
23.252 + // http://wiki.openstreetmap.org/wiki/Slippy_map_tilenames
23.253 + int n = 1 << zoom;
23.254 + double lat = latitude / 180 * Math.PI;
23.255 + x = (longitude + 180.0) / 360.0 * n;
23.256 + y = (1.0 - Math.Log(Math.Tan(lat) + 1.0 / Math.Cos(lat)) / Math.PI) / 2.0 * n;
23.257 + }
23.258 +
23.259 + /// <summary>
23.260 + /// Transforms a tile coordinate (x,y) to a position.
23.261 + /// </summary>
23.262 + /// <param name="x">The x.</param>
23.263 + /// <param name="y">The y.</param>
23.264 + /// <param name="zoom">The zoom.</param>
23.265 + /// <param name="latitude">The latitude.</param>
23.266 + /// <param name="longitude">The longitude.</param>
23.267 + private static void TileToLatLon(double x, double y, int zoom, out double latitude, out double longitude)
23.268 + {
23.269 + int n = 1 << zoom;
23.270 + longitude = (x / n * 360.0) - 180.0;
23.271 + double lat = Math.Atan(Math.Sinh(Math.PI * (1 - (2 * y / n))));
23.272 + latitude = lat * 180.0 / Math.PI;
23.273 + }
23.274 +
23.275 + /// <summary>
23.276 + /// Gets the image from the specified uri.
23.277 + /// </summary>
23.278 + /// <param name="uri">The URI.</param>
23.279 + /// <param name="async">Get the image asynchronously if set to <c>true</c>. The plot model will be invalidated when the image has been downloaded.</param>
23.280 + /// <returns>
23.281 + /// The image.
23.282 + /// </returns>
23.283 + /// <remarks>
23.284 + /// This method gets the image from cache, or starts an async download.
23.285 + /// </remarks>
23.286 + private OxyImage GetImage(string uri, bool async)
23.287 + {
23.288 + OxyImage img;
23.289 + if (this.images.TryGetValue(uri, out img))
23.290 + {
23.291 + return img;
23.292 + }
23.293 +
23.294 + if (!async)
23.295 + {
23.296 + return this.Download(uri);
23.297 + }
23.298 +
23.299 + lock (this.queue)
23.300 + {
23.301 + // 'reserve' an image (otherwise multiple downloads of the same uri may happen)
23.302 + this.images[uri] = null;
23.303 + this.queue.Enqueue(uri);
23.304 + }
23.305 +
23.306 + this.BeginDownload();
23.307 + return null;
23.308 + }
23.309 +
23.310 + /// <summary>
23.311 + /// Downloads the image from the specified URI.
23.312 + /// </summary>
23.313 + /// <param name="uri">The URI.</param>
23.314 + /// <returns>The image</returns>
23.315 + private OxyImage Download(string uri)
23.316 + {
23.317 + OxyImage img = null;
23.318 + var mre = new ManualResetEvent(false);
23.319 + var request = (HttpWebRequest)WebRequest.Create(uri);
23.320 + request.Method = "GET";
23.321 + request.BeginGetResponse(
23.322 + r =>
23.323 + {
23.324 + try
23.325 + {
23.326 + if (request.HaveResponse)
23.327 + {
23.328 + var response = request.EndGetResponse(r);
23.329 + var stream = response.GetResponseStream();
23.330 +
23.331 + var ms = new MemoryStream();
23.332 + stream.CopyTo(ms);
23.333 + var buffer = ms.ToArray();
23.334 +
23.335 + img = new OxyImage(buffer);
23.336 + this.images[uri] = img;
23.337 + }
23.338 +
23.339 + }
23.340 + catch (Exception e)
23.341 + {
23.342 + var ie = e;
23.343 + while (ie != null)
23.344 + {
23.345 + System.Diagnostics.Debug.WriteLine(ie.Message);
23.346 + ie = ie.InnerException;
23.347 + }
23.348 + }
23.349 + finally
23.350 + {
23.351 + mre.Set();
23.352 + }
23.353 + },
23.354 + request);
23.355 +
23.356 + mre.WaitOne();
23.357 + return img;
23.358 + }
23.359 +
23.360 + /// <summary>
23.361 + /// Starts the next download in the queue.
23.362 + /// </summary>
23.363 + private void BeginDownload()
23.364 + {
23.365 + if (this.numberOfDownloads >= this.MaxNumberOfDownloads)
23.366 + {
23.367 + return;
23.368 + }
23.369 +
23.370 + string uri = this.queue.Dequeue();
23.371 + var request = (HttpWebRequest)WebRequest.Create(uri);
23.372 + request.Method = "GET";
23.373 + Interlocked.Increment(ref this.numberOfDownloads);
23.374 + request.BeginGetResponse(
23.375 + r =>
23.376 + {
23.377 + Interlocked.Decrement(ref this.numberOfDownloads);
23.378 + try
23.379 + {
23.380 + if (request.HaveResponse)
23.381 + {
23.382 + var response = request.EndGetResponse(r);
23.383 + var stream = response.GetResponseStream();
23.384 + this.DownloadCompleted(uri, stream);
23.385 + }
23.386 + }
23.387 + catch (Exception e)
23.388 + {
23.389 + var ie = e;
23.390 + while (ie != null)
23.391 + {
23.392 + System.Diagnostics.Debug.WriteLine(ie.Message);
23.393 + ie = ie.InnerException;
23.394 + }
23.395 + }
23.396 + },
23.397 + request);
23.398 + }
23.399 +
23.400 + /// <summary>
23.401 + /// The download completed, set the image.
23.402 + /// </summary>
23.403 + /// <param name="uri">The URI.</param>
23.404 + /// <param name="result">The result.</param>
23.405 + private void DownloadCompleted(string uri, Stream result)
23.406 + {
23.407 + if (result == null)
23.408 + {
23.409 + return;
23.410 + }
23.411 +
23.412 + var ms = new MemoryStream();
23.413 + result.CopyTo(ms);
23.414 + var buffer = ms.ToArray();
23.415 +
23.416 + var img = new OxyImage(buffer);
23.417 + this.images[uri] = img;
23.418 +
23.419 + lock (this.queue)
23.420 + {
23.421 + // Clear old items in the queue, new ones will be added when the plot is refreshed
23.422 + foreach (var queuedUri in this.queue)
23.423 + {
23.424 + // Remove the 'reserved' image
23.425 + this.images.Remove(queuedUri);
23.426 + }
23.427 +
23.428 + this.queue.Clear();
23.429 + }
23.430 +
23.431 + this.PlotModel.InvalidatePlot(false);
23.432 + if (this.queue.Count > 0)
23.433 + {
23.434 + this.BeginDownload();
23.435 + }
23.436 + }
23.437 +
23.438 + /// <summary>
23.439 + /// Gets the tile URI.
23.440 + /// </summary>
23.441 + /// <param name="x">
23.442 + /// The tile x.
23.443 + /// </param>
23.444 + /// <param name="y">
23.445 + /// The tile y.
23.446 + /// </param>
23.447 + /// <param name="zoom">
23.448 + /// The zoom.
23.449 + /// </param>
23.450 + /// <returns>
23.451 + /// The uri.
23.452 + /// </returns>
23.453 + private string GetTileUri(int x, int y, int zoom)
23.454 + {
23.455 + string url = this.Url.Replace("{X}", x.ToString(CultureInfo.InvariantCulture));
23.456 + url = url.Replace("{Y}", y.ToString(CultureInfo.InvariantCulture));
23.457 + return url.Replace("{Z}", zoom.ToString(CultureInfo.InvariantCulture));
23.458 + }
23.459 + }
23.460 +}
23.461 \ No newline at end of file
24.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
24.2 +++ b/External/OxyPlot/OxyPlot/Axes/AngleAxis.cs Sat Jun 08 16:53:22 2013 +0000
24.3 @@ -0,0 +1,184 @@
24.4 +// --------------------------------------------------------------------------------------------------------------------
24.5 +// <copyright file="AngleAxis.cs" company="OxyPlot">
24.6 +// The MIT License (MIT)
24.7 +//
24.8 +// Copyright (c) 2012 Oystein Bjorke
24.9 +//
24.10 +// Permission is hereby granted, free of charge, to any person obtaining a
24.11 +// copy of this software and associated documentation files (the
24.12 +// "Software"), to deal in the Software without restriction, including
24.13 +// without limitation the rights to use, copy, modify, merge, publish,
24.14 +// distribute, sublicense, and/or sell copies of the Software, and to
24.15 +// permit persons to whom the Software is furnished to do so, subject to
24.16 +// the following conditions:
24.17 +//
24.18 +// The above copyright notice and this permission notice shall be included
24.19 +// in all copies or substantial portions of the Software.
24.20 +//
24.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
24.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
24.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
24.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
24.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
24.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
24.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24.28 +// </copyright>
24.29 +// <summary>
24.30 +// Represents an angular axis for polar plots.
24.31 +// </summary>
24.32 +// --------------------------------------------------------------------------------------------------------------------
24.33 +namespace OxyPlot.Axes
24.34 +{
24.35 + using System;
24.36 +
24.37 + /// <summary>
24.38 + /// Represents an angular axis for polar plots.
24.39 + /// </summary>
24.40 + public class AngleAxis : LinearAxis
24.41 + {
24.42 + /// <summary>
24.43 + /// Initializes a new instance of the <see cref="AngleAxis"/> class.
24.44 + /// </summary>
24.45 + public AngleAxis()
24.46 + {
24.47 + this.IsPanEnabled = false;
24.48 + this.IsZoomEnabled = false;
24.49 + this.MajorGridlineStyle = LineStyle.Solid;
24.50 + this.MinorGridlineStyle = LineStyle.Solid;
24.51 + this.StartAngle = 0;
24.52 + this.EndAngle = 360;
24.53 + }
24.54 +
24.55 + /// <summary>
24.56 + /// Initializes a new instance of the <see cref="AngleAxis"/> class.
24.57 + /// </summary>
24.58 + /// <param name="minimum">
24.59 + /// The minimum.
24.60 + /// </param>
24.61 + /// <param name="maximum">
24.62 + /// The maximum.
24.63 + /// </param>
24.64 + /// <param name="majorStep">
24.65 + /// The major step.
24.66 + /// </param>
24.67 + /// <param name="minorStep">
24.68 + /// The minor step.
24.69 + /// </param>
24.70 + /// <param name="title">
24.71 + /// The title.
24.72 + /// </param>
24.73 + public AngleAxis(
24.74 + double minimum = double.NaN,
24.75 + double maximum = double.NaN,
24.76 + double majorStep = double.NaN,
24.77 + double minorStep = double.NaN,
24.78 + string title = null)
24.79 + : this()
24.80 + {
24.81 + this.Minimum = minimum;
24.82 + this.Maximum = maximum;
24.83 + this.MajorStep = majorStep;
24.84 + this.MinorStep = minorStep;
24.85 + this.Title = title;
24.86 + this.StartAngle = 0;
24.87 + this.EndAngle = 360;
24.88 + }
24.89 +
24.90 + /// <summary>
24.91 + /// Gets or sets the start angle (degrees).
24.92 + /// </summary>
24.93 + public double StartAngle { get; set; }
24.94 +
24.95 + /// <summary>
24.96 + /// Gets or sets the end angle (degrees).
24.97 + /// </summary>
24.98 + public double EndAngle { get; set; }
24.99 +
24.100 + /// <summary>
24.101 + /// Inverse transform the specified screen point.
24.102 + /// </summary>
24.103 + /// <param name="x">The x coordinate.</param>
24.104 + /// <param name="y">The y coordinate.</param>
24.105 + /// <param name="yaxis">The y-axis.</param>
24.106 + /// <returns>
24.107 + /// The data point.
24.108 + /// </returns>
24.109 + public override DataPoint InverseTransform(double x, double y, Axis yaxis)
24.110 + {
24.111 + throw new InvalidOperationException("Angle axis should always be the y-axis.");
24.112 + }
24.113 +
24.114 + /// <summary>
24.115 + /// Determines whether the axis is used for X/Y values.
24.116 + /// </summary>
24.117 + /// <returns>
24.118 + /// <c>true</c> if it is an XY axis; otherwise, <c>false</c> .
24.119 + /// </returns>
24.120 + public override bool IsXyAxis()
24.121 + {
24.122 + return false;
24.123 + }
24.124 +
24.125 + /// <summary>
24.126 + /// Renders the axis on the specified render context.
24.127 + /// </summary>
24.128 + /// <param name="rc">The render context.</param>
24.129 + /// <param name="model">The model.</param>
24.130 + /// <param name="axisLayer">The rendering order.</param>
24.131 + /// <param name="pass"></param>
24.132 + public override void Render(IRenderContext rc, PlotModel model, AxisLayer axisLayer, int pass)
24.133 + {
24.134 + if (this.Layer != axisLayer)
24.135 + {
24.136 + return;
24.137 + }
24.138 +
24.139 + var r = new AngleAxisRenderer(rc, model);
24.140 + r.Render(this, pass);
24.141 + }
24.142 +
24.143 + /// <summary>
24.144 + /// Transforms the specified point to screen coordinates.
24.145 + /// </summary>
24.146 + /// <param name="x">
24.147 + /// The x value (for the current axis).
24.148 + /// </param>
24.149 + /// <param name="y">
24.150 + /// The y value.
24.151 + /// </param>
24.152 + /// <param name="yaxis">
24.153 + /// The y axis.
24.154 + /// </param>
24.155 + /// <returns>
24.156 + /// The transformed point.
24.157 + /// </returns>
24.158 + public override ScreenPoint Transform(double x, double y, Axis yaxis)
24.159 + {
24.160 + throw new InvalidOperationException("Angle axis should always be the y-axis.");
24.161 + }
24.162 +
24.163 + /// <summary>
24.164 + /// The update transform.
24.165 + /// </summary>
24.166 + /// <param name="bounds">
24.167 + /// The bounds.
24.168 + /// </param>
24.169 + internal override void UpdateTransform(OxyRect bounds)
24.170 + {
24.171 + double x0 = bounds.Left;
24.172 + double x1 = bounds.Right;
24.173 + double y0 = bounds.Bottom;
24.174 + double y1 = bounds.Top;
24.175 +
24.176 + this.ScreenMin = new ScreenPoint(x0, y1);
24.177 + this.ScreenMax = new ScreenPoint(x1, y0);
24.178 +
24.179 + double startAngle = this.StartAngle / 180 * Math.PI;
24.180 + double endAngle = this.EndAngle / 180 * Math.PI;
24.181 +
24.182 + this.Scale = (endAngle - startAngle) / (this.ActualMaximum - this.ActualMinimum);
24.183 + this.Offset = this.ActualMinimum - (startAngle / this.Scale);
24.184 + }
24.185 +
24.186 + }
24.187 +}
24.188 \ No newline at end of file
25.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
25.2 +++ b/External/OxyPlot/OxyPlot/Axes/Axis.cs Sat Jun 08 16:53:22 2013 +0000
25.3 @@ -0,0 +1,1753 @@
25.4 +// --------------------------------------------------------------------------------------------------------------------
25.5 +// <copyright file="Axis.cs" company="OxyPlot">
25.6 +// The MIT License (MIT)
25.7 +//
25.8 +// Copyright (c) 2012 Oystein Bjorke
25.9 +//
25.10 +// Permission is hereby granted, free of charge, to any person obtaining a
25.11 +// copy of this software and associated documentation files (the
25.12 +// "Software"), to deal in the Software without restriction, including
25.13 +// without limitation the rights to use, copy, modify, merge, publish,
25.14 +// distribute, sublicense, and/or sell copies of the Software, and to
25.15 +// permit persons to whom the Software is furnished to do so, subject to
25.16 +// the following conditions:
25.17 +//
25.18 +// The above copyright notice and this permission notice shall be included
25.19 +// in all copies or substantial portions of the Software.
25.20 +//
25.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
25.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
25.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
25.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
25.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
25.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
25.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
25.28 +// </copyright>
25.29 +// <summary>
25.30 +// Abstract base class for axes.
25.31 +// </summary>
25.32 +// --------------------------------------------------------------------------------------------------------------------
25.33 +namespace OxyPlot.Axes
25.34 +{
25.35 + using System;
25.36 + using System.Collections.Generic;
25.37 + using System.Diagnostics.CodeAnalysis;
25.38 + using System.Globalization;
25.39 +
25.40 + using OxyPlot.Series;
25.41 +
25.42 + /// <summary>
25.43 + /// Provides an abstract base class for axes.
25.44 + /// </summary>
25.45 + public abstract class Axis : PlotElement
25.46 + {
25.47 + /// <summary>
25.48 + /// Exponent function.
25.49 + /// </summary>
25.50 + protected static readonly Func<double, double> Exponent = x => Math.Round(Math.Log(Math.Abs(x), 10));
25.51 +
25.52 + /// <summary>
25.53 + /// Mantissa function. http://en.wikipedia.org/wiki/Mantissa
25.54 + /// </summary>
25.55 + protected static readonly Func<double, double> Mantissa = x => x / Math.Pow(10, Exponent(x));
25.56 +
25.57 + /// <summary>
25.58 + /// The offset.
25.59 + /// </summary>
25.60 + [SuppressMessage("StyleCop.CSharp.MaintainabilityRules", "SA1401:FieldsMustBePrivate",
25.61 + Justification = "Reviewed. Suppression is OK here.")]
25.62 + protected double offset;
25.63 +
25.64 + /// <summary>
25.65 + /// The scale.
25.66 + /// </summary>
25.67 + [SuppressMessage("StyleCop.CSharp.MaintainabilityRules", "SA1401:FieldsMustBePrivate",
25.68 + Justification = "Reviewed. Suppression is OK here.")]
25.69 + protected double scale;
25.70 +
25.71 + /// <summary>
25.72 + /// The position.
25.73 + /// </summary>
25.74 + private AxisPosition position;
25.75 +
25.76 + /// <summary>
25.77 + /// Initializes a new instance of the <see cref="Axis"/> class.
25.78 + /// </summary>
25.79 + protected Axis()
25.80 + {
25.81 + this.Position = AxisPosition.Left;
25.82 + this.PositionTier = 0;
25.83 + this.IsAxisVisible = true;
25.84 + this.Layer = AxisLayer.BelowSeries;
25.85 +
25.86 + this.ViewMaximum = double.NaN;
25.87 + this.ViewMinimum = double.NaN;
25.88 +
25.89 + this.AbsoluteMaximum = double.MaxValue;
25.90 + this.AbsoluteMinimum = double.MinValue;
25.91 +
25.92 + this.Minimum = double.NaN;
25.93 + this.Maximum = double.NaN;
25.94 + this.MinorStep = double.NaN;
25.95 + this.MajorStep = double.NaN;
25.96 +
25.97 + this.MinimumPadding = 0.01;
25.98 + this.MaximumPadding = 0.01;
25.99 + this.MinimumRange = 0;
25.100 +
25.101 + this.TickStyle = TickStyle.Outside;
25.102 + this.TicklineColor = OxyColors.Black;
25.103 +
25.104 + this.AxislineStyle = LineStyle.None;
25.105 + this.AxislineColor = OxyColors.Black;
25.106 + this.AxislineThickness = 1.0;
25.107 +
25.108 + this.MajorGridlineStyle = LineStyle.None;
25.109 + this.MajorGridlineColor = OxyColor.FromArgb(0x40, 0, 0, 0);
25.110 + this.MajorGridlineThickness = 1;
25.111 +
25.112 + this.MinorGridlineStyle = LineStyle.None;
25.113 + this.MinorGridlineColor = OxyColor.FromArgb(0x20, 0, 0, 0x00);
25.114 + this.MinorGridlineThickness = 1;
25.115 +
25.116 + this.ExtraGridlineStyle = LineStyle.Solid;
25.117 + this.ExtraGridlineColor = OxyColors.Black;
25.118 + this.ExtraGridlineThickness = 1;
25.119 +
25.120 + this.ShowMinorTicks = true;
25.121 +
25.122 + this.MinorTickSize = 4;
25.123 + this.MajorTickSize = 7;
25.124 +
25.125 + this.StartPosition = 0;
25.126 + this.EndPosition = 1;
25.127 +
25.128 + this.TitlePosition = 0.5;
25.129 + this.TitleFormatString = "{0} [{1}]";
25.130 + this.TitleClippingLength = 0.9;
25.131 + this.TitleColor = null;
25.132 + this.TitleFontSize = double.NaN;
25.133 + this.TitleFontWeight = FontWeights.Normal;
25.134 + this.ClipTitle = true;
25.135 +
25.136 + this.Angle = 0;
25.137 +
25.138 + this.IsZoomEnabled = true;
25.139 + this.IsPanEnabled = true;
25.140 +
25.141 + this.FilterMinValue = double.MinValue;
25.142 + this.FilterMaxValue = double.MaxValue;
25.143 + this.FilterFunction = null;
25.144 +
25.145 + this.IntervalLength = 60;
25.146 +
25.147 + this.AxisTitleDistance = 4;
25.148 + this.AxisTickToLabelDistance = 4;
25.149 + }
25.150 +
25.151 + /// <summary>
25.152 + /// Initializes a new instance of the <see cref="Axis"/> class.
25.153 + /// </summary>
25.154 + /// <param name="pos">
25.155 + /// The position of the axis.
25.156 + /// </param>
25.157 + /// <param name="minimum">
25.158 + /// The minimum value.
25.159 + /// </param>
25.160 + /// <param name="maximum">
25.161 + /// The maximum value.
25.162 + /// </param>
25.163 + /// <param name="title">
25.164 + /// The axis title.
25.165 + /// </param>
25.166 + protected Axis(AxisPosition pos, double minimum, double maximum, string title = null)
25.167 + : this()
25.168 + {
25.169 + this.Position = pos;
25.170 + this.Minimum = minimum;
25.171 + this.Maximum = maximum;
25.172 +
25.173 + this.AbsoluteMaximum = double.NaN;
25.174 + this.AbsoluteMinimum = double.NaN;
25.175 +
25.176 + this.Title = title;
25.177 + }
25.178 +
25.179 + /// <summary>
25.180 + /// Occurs when the axis has been changed (by zooming, panning or resetting).
25.181 + /// </summary>
25.182 + public event EventHandler<AxisChangedEventArgs> AxisChanged;
25.183 +
25.184 + /// <summary>
25.185 + /// Gets or sets the absolute maximum. This is only used for the UI control. It will not be possible to zoom/pan beyond this limit.
25.186 + /// </summary>
25.187 + /// <value> The absolute maximum. </value>
25.188 + public double AbsoluteMaximum { get; set; }
25.189 +
25.190 + /// <summary>
25.191 + /// Gets or sets the absolute minimum. This is only used for the UI control. It will not be possible to zoom/pan beyond this limit.
25.192 + /// </summary>
25.193 + /// <value> The absolute minimum. </value>
25.194 + public double AbsoluteMinimum { get; set; }
25.195 +
25.196 + /// <summary>
25.197 + /// Gets the actual culture.
25.198 + /// </summary>
25.199 + /// <remarks>
25.200 + /// The culture is defined in the parent PlotModel.
25.201 + /// </remarks>
25.202 + public CultureInfo ActualCulture
25.203 + {
25.204 + get
25.205 + {
25.206 + return this.PlotModel != null ? this.PlotModel.ActualCulture : CultureInfo.CurrentCulture;
25.207 + }
25.208 + }
25.209 +
25.210 + /// <summary>
25.211 + /// Gets or sets the actual major step.
25.212 + /// </summary>
25.213 + public double ActualMajorStep { get; protected set; }
25.214 +
25.215 + /// <summary>
25.216 + /// Gets or sets the actual maximum value of the axis.
25.217 + /// </summary>
25.218 + /// <remarks>
25.219 + /// If ViewMaximum is not NaN, this value will be defined by ViewMaximum.
25.220 + /// Otherwise, if Maximum is not NaN, this value will be defined by Maximum.
25.221 + /// Otherwise, this value will be defined by the maximum (+padding) of the data.
25.222 + /// </remarks>
25.223 + public double ActualMaximum { get; protected set; }
25.224 +
25.225 + /// <summary>
25.226 + /// Gets or sets the actual minimum value of the axis.
25.227 + /// </summary>
25.228 + /// <remarks>
25.229 + /// If ViewMinimum is not NaN, this value will be defined by ViewMinimum.
25.230 + /// Otherwise, if Minimum is not NaN, this value will be defined by Minimum.
25.231 + /// Otherwise this value will be defined by the minimum (+padding) of the data.
25.232 + /// </remarks>
25.233 + public double ActualMinimum { get; protected set; }
25.234 +
25.235 + /// <summary>
25.236 + /// Gets or sets the maximum value of the data displayed on this axis.
25.237 + /// </summary>
25.238 + /// <value>The data maximum.</value>
25.239 + public double DataMaximum { get; protected set; }
25.240 +
25.241 + /// <summary>
25.242 + /// Gets or sets the minimum value of the data displayed on this axis.
25.243 + /// </summary>
25.244 + /// <value>The data minimum.</value>
25.245 + public double DataMinimum { get; protected set; }
25.246 +
25.247 + /// <summary>
25.248 + /// Gets or sets the actual minor step.
25.249 + /// </summary>
25.250 + public double ActualMinorStep { get; protected set; }
25.251 +
25.252 + /// <summary>
25.253 + /// Gets or sets the actual string format being used.
25.254 + /// </summary>
25.255 + public string ActualStringFormat { get; protected set; }
25.256 +
25.257 + /// <summary>
25.258 + /// Gets the actual title (including Unit if Unit is set).
25.259 + /// </summary>
25.260 + /// <value> The actual title. </value>
25.261 + public string ActualTitle
25.262 + {
25.263 + get
25.264 + {
25.265 + if (this.Unit != null)
25.266 + {
25.267 + return string.Format(this.TitleFormatString, this.Title, this.Unit);
25.268 + }
25.269 +
25.270 + return this.Title;
25.271 + }
25.272 + }
25.273 +
25.274 + /// <summary>
25.275 + /// Gets or sets the angle for the axis values.
25.276 + /// </summary>
25.277 + public double Angle { get; set; }
25.278 +
25.279 + /// <summary>
25.280 + /// Gets or sets the distance from axis tick to number label.
25.281 + /// </summary>
25.282 + /// <value> The axis tick to label distance. </value>
25.283 + public double AxisTickToLabelDistance { get; set; }
25.284 +
25.285 + /// <summary>
25.286 + /// Gets or sets the distance from axis number to axis title.
25.287 + /// </summary>
25.288 + /// <value> The axis title distance. </value>
25.289 + public double AxisTitleDistance { get; set; }
25.290 +
25.291 + /// <summary>
25.292 + /// Gets or sets the color of the axis line.
25.293 + /// </summary>
25.294 + public OxyColor AxislineColor { get; set; }
25.295 +
25.296 + /// <summary>
25.297 + /// Gets or sets the axis line.
25.298 + /// </summary>
25.299 + public LineStyle AxislineStyle { get; set; }
25.300 +
25.301 + /// <summary>
25.302 + /// Gets or sets the axis line.
25.303 + /// </summary>
25.304 + public double AxislineThickness { get; set; }
25.305 +
25.306 + /// <summary>
25.307 + /// Gets or sets a value indicating whether to clip the axis title.
25.308 + /// </summary>
25.309 + /// <remarks>
25.310 + /// The default value is true.
25.311 + /// </remarks>
25.312 + public bool ClipTitle { get; set; }
25.313 +
25.314 + /// <summary>
25.315 + /// Gets or sets the end position of the axis on the plot area. This is a fraction from 0(bottom/left) to 1(top/right).
25.316 + /// </summary>
25.317 + public double EndPosition { get; set; }
25.318 +
25.319 + /// <summary>
25.320 + /// Gets or sets the color of the extra gridlines.
25.321 + /// </summary>
25.322 + public OxyColor ExtraGridlineColor { get; set; }
25.323 +
25.324 + /// <summary>
25.325 + /// Gets or sets the extra gridlines line style.
25.326 + /// </summary>
25.327 + public LineStyle ExtraGridlineStyle { get; set; }
25.328 +
25.329 + /// <summary>
25.330 + /// Gets or sets the extra gridline thickness.
25.331 + /// </summary>
25.332 + public double ExtraGridlineThickness { get; set; }
25.333 +
25.334 + /// <summary>
25.335 + /// Gets or sets the values for extra gridlines.
25.336 + /// </summary>
25.337 + public double[] ExtraGridlines { get; set; }
25.338 +
25.339 + /// <summary>
25.340 + /// Gets or sets the filter function.
25.341 + /// </summary>
25.342 + /// <value> The filter function. </value>
25.343 + public Func<double, bool> FilterFunction { get; set; }
25.344 +
25.345 + /// <summary>
25.346 + /// Gets or sets the maximum value that can be shown using this axis. Values greater or equal to this value will not be shown.
25.347 + /// </summary>
25.348 + /// <value> The filter max value. </value>
25.349 + public double FilterMaxValue { get; set; }
25.350 +
25.351 + /// <summary>
25.352 + /// Gets or sets the minimum value that can be shown using this axis. Values smaller or equal to this value will not be shown.
25.353 + /// </summary>
25.354 + /// <value> The filter min value. </value>
25.355 + public double FilterMinValue { get; set; }
25.356 +
25.357 + /// <summary>
25.358 + /// Gets or sets the length of the interval (screen length). The available length of the axis will be divided by this length to get the approximate number of major intervals on the axis. The default value is 60.
25.359 + /// </summary>
25.360 + public double IntervalLength { get; set; }
25.361 +
25.362 + /// <summary>
25.363 + /// Gets or sets a value indicating whether this axis is visible.
25.364 + /// </summary>
25.365 + public bool IsAxisVisible { get; set; }
25.366 +
25.367 + /// <summary>
25.368 + /// Gets or sets a value indicating whether pan is enabled.
25.369 + /// </summary>
25.370 + public bool IsPanEnabled { get; set; }
25.371 +
25.372 + /// <summary>
25.373 + /// Gets a value indicating whether this axis is reversed. It is reversed if StartPosition>EndPosition.
25.374 + /// </summary>
25.375 + public bool IsReversed
25.376 + {
25.377 + get
25.378 + {
25.379 + return this.StartPosition > this.EndPosition;
25.380 + }
25.381 + }
25.382 +
25.383 + /// <summary>
25.384 + /// Gets or sets a value indicating whether zoom is enabled.
25.385 + /// </summary>
25.386 + public bool IsZoomEnabled { get; set; }
25.387 +
25.388 + /// <summary>
25.389 + /// Gets or sets the key of the axis. This can be used to find an axis if you have defined multiple axes in a plot.
25.390 + /// </summary>
25.391 + public string Key { get; set; }
25.392 +
25.393 + /// <summary>
25.394 + /// Gets or sets the layer.
25.395 + /// </summary>
25.396 + /// <value> The layer. </value>
25.397 + public AxisLayer Layer { get; set; }
25.398 +
25.399 + /// <summary>
25.400 + /// Gets or sets the color of the major gridline.
25.401 + /// </summary>
25.402 + public OxyColor MajorGridlineColor { get; set; }
25.403 +
25.404 + /// <summary>
25.405 + /// Gets or sets the major gridline style.
25.406 + /// </summary>
25.407 + public LineStyle MajorGridlineStyle { get; set; }
25.408 +
25.409 + /// <summary>
25.410 + /// Gets or sets the major gridline thickness.
25.411 + /// </summary>
25.412 + public double MajorGridlineThickness { get; set; }
25.413 +
25.414 + /// <summary>
25.415 + /// Gets or sets the major step. (the interval between large ticks with numbers).
25.416 + /// </summary>
25.417 + public double MajorStep { get; set; }
25.418 +
25.419 + /// <summary>
25.420 + /// Gets or sets the size of the major tick.
25.421 + /// </summary>
25.422 + public double MajorTickSize { get; set; }
25.423 +
25.424 + /// <summary>
25.425 + /// Gets or sets the maximum value of the axis.
25.426 + /// </summary>
25.427 + public double Maximum { get; set; }
25.428 +
25.429 + /// <summary>
25.430 + /// Gets or sets the 'padding' fraction of the maximum value. A value of 0.01 gives 1% more space on the maximum end of the axis. This property is not used if the Maximum property is set.
25.431 + /// </summary>
25.432 + public double MaximumPadding { get; set; }
25.433 +
25.434 + /// <summary>
25.435 + /// Gets or sets the minimum value of the axis.
25.436 + /// </summary>
25.437 + public double Minimum { get; set; }
25.438 +
25.439 + /// <summary>
25.440 + /// Gets or sets the 'padding' fraction of the minimum value. A value of 0.01 gives 1% more space on the minimum end of the axis. This property is not used if the Minimum property is set.
25.441 + /// </summary>
25.442 + public double MinimumPadding { get; set; }
25.443 +
25.444 + /// <summary>
25.445 + /// Gets or sets the minimum range of the axis. Setting this property ensures that ActualMaximum-ActualMinimum > MinimumRange.
25.446 + /// </summary>
25.447 + public double MinimumRange { get; set; }
25.448 +
25.449 + /// <summary>
25.450 + /// Gets or sets the color of the minor gridline.
25.451 + /// </summary>
25.452 + public OxyColor MinorGridlineColor { get; set; }
25.453 +
25.454 + /// <summary>
25.455 + /// Gets or sets the minor gridline style.
25.456 + /// </summary>
25.457 + public LineStyle MinorGridlineStyle { get; set; }
25.458 +
25.459 + /// <summary>
25.460 + /// Gets or sets the minor gridline thickness.
25.461 + /// </summary>
25.462 + public double MinorGridlineThickness { get; set; }
25.463 +
25.464 + /// <summary>
25.465 + /// Gets or sets the minor step (the interval between small ticks without number).
25.466 + /// </summary>
25.467 + public double MinorStep { get; set; }
25.468 +
25.469 + /// <summary>
25.470 + /// Gets or sets the size of the minor tick.
25.471 + /// </summary>
25.472 + public double MinorTickSize { get; set; }
25.473 +
25.474 + /// <summary>
25.475 + /// Gets or sets the offset. This is used to transform between data and screen coordinates.
25.476 + /// </summary>
25.477 + public double Offset
25.478 + {
25.479 + get
25.480 + {
25.481 + return this.offset;
25.482 + }
25.483 +
25.484 + protected set
25.485 + {
25.486 + this.offset = value;
25.487 + }
25.488 + }
25.489 +
25.490 + /// <summary>
25.491 + /// Gets or sets the position of the axis.
25.492 + /// </summary>
25.493 + public AxisPosition Position
25.494 + {
25.495 + get
25.496 + {
25.497 + return this.position;
25.498 + }
25.499 +
25.500 + set
25.501 + {
25.502 + this.position = value;
25.503 + }
25.504 + }
25.505 +
25.506 + /// <summary>
25.507 + /// Gets or sets a value indicating whether the axis should be positioned on the zero-crossing of the related axis.
25.508 + /// </summary>
25.509 + public bool PositionAtZeroCrossing { get; set; }
25.510 +
25.511 + /// <summary>
25.512 + /// Gets or sets the position tier which defines in which tier the axis is displayed.
25.513 + /// </summary>
25.514 + /// <remarks>
25.515 + /// The bigger the value the the further afar is the axis from the graph.
25.516 + /// </remarks>
25.517 + public int PositionTier { get; set; }
25.518 +
25.519 + /// <summary>
25.520 + /// Gets or sets the related axis. This is used for polar coordinate systems where the angle and magnitude axes are related.
25.521 + /// </summary>
25.522 + public Axis RelatedAxis { get; set; }
25.523 +
25.524 + /// <summary>
25.525 + /// Gets or sets the scaling factor of the axis. This is used to transform between data and screen coordinates.
25.526 + /// </summary>
25.527 + public double Scale
25.528 + {
25.529 + get
25.530 + {
25.531 + return this.scale;
25.532 + }
25.533 +
25.534 + protected set
25.535 + {
25.536 + this.scale = value;
25.537 + }
25.538 + }
25.539 +
25.540 + /// <summary>
25.541 + /// Gets or sets the screen coordinate of the Maximum point on the axis.
25.542 + /// </summary>
25.543 + public ScreenPoint ScreenMax { get; protected set; }
25.544 +
25.545 + /// <summary>
25.546 + /// Gets or sets the screen coordinate of the Minimum point on the axis.
25.547 + /// </summary>
25.548 + public ScreenPoint ScreenMin { get; protected set; }
25.549 +
25.550 + /// <summary>
25.551 + /// Gets or sets a value indicating whether minor ticks should be shown.
25.552 + /// </summary>
25.553 + public bool ShowMinorTicks { get; set; }
25.554 +
25.555 + /// <summary>
25.556 + /// Gets or sets the start position of the axis on the plot area. This is a fraction from 0(bottom/left) to 1(top/right).
25.557 + /// </summary>
25.558 + public double StartPosition { get; set; }
25.559 +
25.560 + /// <summary>
25.561 + /// Gets or sets the string format used for formatting the axis values.
25.562 + /// </summary>
25.563 + public string StringFormat { get; set; }
25.564 +
25.565 + /// <summary>
25.566 + /// Gets or sets the tick style (both for major and minor ticks).
25.567 + /// </summary>
25.568 + public TickStyle TickStyle { get; set; }
25.569 +
25.570 + /// <summary>
25.571 + /// Gets or sets the color of the ticks (both major and minor ticks).
25.572 + /// </summary>
25.573 + public OxyColor TicklineColor { get; set; }
25.574 +
25.575 + /// <summary>
25.576 + /// Gets or sets the title of the axis.
25.577 + /// </summary>
25.578 + public string Title { get; set; }
25.579 +
25.580 + /// <summary>
25.581 + /// Gets or sets the length of the title clipping rectangle (fraction of the available length of the axis).
25.582 + /// </summary>
25.583 + /// <remarks>
25.584 + /// The default value is 0.9
25.585 + /// </remarks>
25.586 + public double TitleClippingLength { get; set; }
25.587 +
25.588 + /// <summary>
25.589 + /// Gets or sets the color of the title.
25.590 + /// </summary>
25.591 + /// <value> The color of the title. </value>
25.592 + /// <remarks>
25.593 + /// If TitleColor is null, the parent PlotModel's TextColor will be used.
25.594 + /// </remarks>
25.595 + public OxyColor TitleColor { get; set; }
25.596 +
25.597 + /// <summary>
25.598 + /// Gets or sets the title font.
25.599 + /// </summary>
25.600 + /// <value> The title font. </value>
25.601 + public string TitleFont { get; set; }
25.602 +
25.603 + /// <summary>
25.604 + /// Gets or sets the size of the title font.
25.605 + /// </summary>
25.606 + /// <value> The size of the title font. </value>
25.607 + public double TitleFontSize { get; set; }
25.608 +
25.609 + /// <summary>
25.610 + /// Gets or sets the title font weight.
25.611 + /// </summary>
25.612 + /// <value> The title font weight. </value>
25.613 + public double TitleFontWeight { get; set; }
25.614 +
25.615 + /// <summary>
25.616 + /// Gets or sets the format string used for formatting the title and unit when unit is defined. If unit is null, only Title is used. The default value is "{0} [{1}]", where {0} uses the Title and {1} uses the Unit.
25.617 + /// </summary>
25.618 + public string TitleFormatString { get; set; }
25.619 +
25.620 + /// <summary>
25.621 + /// Gets or sets the position of the title (0.5 is in the middle).
25.622 + /// </summary>
25.623 + public double TitlePosition { get; set; }
25.624 +
25.625 + /// <summary>
25.626 + /// Gets or sets the tool tip.
25.627 + /// </summary>
25.628 + /// <value> The tool tip. </value>
25.629 + public string ToolTip { get; set; }
25.630 +
25.631 + /// <summary>
25.632 + /// Gets or sets the unit of the axis.
25.633 + /// </summary>
25.634 + public string Unit { get; set; }
25.635 +
25.636 + /// <summary>
25.637 + /// Gets or sets a value indicating whether to use superscript exponential format. This format will convert 1.5E+03 to 1.5·10^{3} and render the superscript properly If StringFormat is null, 1.0E+03 will be converted to 10^{3}
25.638 + /// </summary>
25.639 + public bool UseSuperExponentialFormat { get; set; }
25.640 +
25.641 + /// <summary>
25.642 + /// Gets or sets the position tier max shift.
25.643 + /// </summary>
25.644 + /// <value> The position tier max shift. </value>
25.645 + internal double PositionTierMaxShift { get; set; }
25.646 +
25.647 + /// <summary>
25.648 + /// Gets or sets the position tier min shift.
25.649 + /// </summary>
25.650 + /// <value> The position tier min shift. </value>
25.651 + internal double PositionTierMinShift { get; set; }
25.652 +
25.653 + /// <summary>
25.654 + /// Gets or sets the size of the position tier.
25.655 + /// </summary>
25.656 + /// <value> The size of the position tier. </value>
25.657 + internal double PositionTierSize { get; set; }
25.658 +
25.659 + /// <summary>
25.660 + /// Gets the actual color of the title.
25.661 + /// </summary>
25.662 + /// <value> The actual color of the title. </value>
25.663 + protected internal OxyColor ActualTitleColor
25.664 + {
25.665 + get
25.666 + {
25.667 + return this.TitleColor ?? this.PlotModel.TextColor;
25.668 + }
25.669 + }
25.670 +
25.671 + /// <summary>
25.672 + /// Gets the actual title font.
25.673 + /// </summary>
25.674 + protected internal string ActualTitleFont
25.675 + {
25.676 + get
25.677 + {
25.678 + return this.TitleFont ?? this.PlotModel.DefaultFont;
25.679 + }
25.680 + }
25.681 +
25.682 + /// <summary>
25.683 + /// Gets the actual size of the title font.
25.684 + /// </summary>
25.685 + /// <value> The actual size of the title font. </value>
25.686 + protected internal double ActualTitleFontSize
25.687 + {
25.688 + get
25.689 + {
25.690 + return !double.IsNaN(this.TitleFontSize) ? this.TitleFontSize : this.ActualFontSize;
25.691 + }
25.692 + }
25.693 +
25.694 + /// <summary>
25.695 + /// Gets the actual title font weight.
25.696 + /// </summary>
25.697 + protected internal double ActualTitleFontWeight
25.698 + {
25.699 + get
25.700 + {
25.701 + return !double.IsNaN(this.TitleFontWeight) ? this.TitleFontWeight : this.ActualFontWeight;
25.702 + }
25.703 + }
25.704 +
25.705 + /// <summary>
25.706 + /// Gets or sets the current view's maximum. This value is used when the user zooms or pans.
25.707 + /// </summary>
25.708 + /// <value> The view maximum. </value>
25.709 + protected double ViewMaximum { get; set; }
25.710 +
25.711 + /// <summary>
25.712 + /// Gets or sets the current view's minimum. This value is used when the user zooms or pans.
25.713 + /// </summary>
25.714 + /// <value> The view minimum. </value>
25.715 + protected double ViewMinimum { get; set; }
25.716 +
25.717 + /// <summary>
25.718 + /// Transforms the specified point to screen coordinates.
25.719 + /// </summary>
25.720 + /// <param name="p">
25.721 + /// The point.
25.722 + /// </param>
25.723 + /// <param name="xaxis">
25.724 + /// The x axis.
25.725 + /// </param>
25.726 + /// <param name="yaxis">
25.727 + /// The y axis.
25.728 + /// </param>
25.729 + /// <returns>
25.730 + /// The transformed point.
25.731 + /// </returns>
25.732 + public static ScreenPoint Transform(DataPoint p, Axis xaxis, Axis yaxis)
25.733 + {
25.734 + return xaxis.Transform(p.x, p.y, yaxis);
25.735 + }
25.736 +
25.737 + /// <summary>
25.738 + /// Transform the specified screen point to data coordinates.
25.739 + /// </summary>
25.740 + /// <param name="p">The point.</param>
25.741 + /// <param name="xaxis">The x axis.</param>
25.742 + /// <param name="yaxis">The y axis.</param>
25.743 + /// <returns>The data point.</returns>
25.744 + public static DataPoint InverseTransform(ScreenPoint p, Axis xaxis, Axis yaxis)
25.745 + {
25.746 + return xaxis.InverseTransform(p.x, p.y, yaxis);
25.747 + }
25.748 +
25.749 + /// <summary>
25.750 + /// Transforms the specified point to screen coordinates.
25.751 + /// </summary>
25.752 + /// <param name="p">
25.753 + /// The point.
25.754 + /// </param>
25.755 + /// <param name="xaxis">
25.756 + /// The x axis.
25.757 + /// </param>
25.758 + /// <param name="yaxis">
25.759 + /// The y axis.
25.760 + /// </param>
25.761 + /// <returns>
25.762 + /// The transformed point.
25.763 + /// </returns>
25.764 + public static ScreenPoint Transform(IDataPoint p, Axis xaxis, Axis yaxis)
25.765 + {
25.766 + return xaxis.Transform(p.X, p.Y, yaxis);
25.767 + }
25.768 +
25.769 + /// <summary>
25.770 + /// Coerces the actual maximum and minimum values.
25.771 + /// </summary>
25.772 + public virtual void CoerceActualMaxMin()
25.773 + {
25.774 + // Coerce actual minimum
25.775 + if (double.IsNaN(this.ActualMinimum) || double.IsInfinity(this.ActualMinimum))
25.776 + {
25.777 + this.ActualMinimum = 0;
25.778 + }
25.779 +
25.780 + // Coerce actual maximum
25.781 + if (double.IsNaN(this.ActualMaximum) || double.IsInfinity(this.ActualMaximum))
25.782 + {
25.783 + this.ActualMaximum = 100;
25.784 + }
25.785 +
25.786 + if (this.ActualMaximum <= this.ActualMinimum)
25.787 + {
25.788 + this.ActualMaximum = this.ActualMinimum + 100;
25.789 + }
25.790 +
25.791 + // Coerce the minimum range
25.792 + double range = this.ActualMaximum - this.ActualMinimum;
25.793 + if (range < this.MinimumRange)
25.794 + {
25.795 + double avg = (this.ActualMaximum + this.ActualMinimum) * 0.5;
25.796 + this.ActualMinimum = avg - (this.MinimumRange * 0.5);
25.797 + this.ActualMaximum = avg + (this.MinimumRange * 0.5);
25.798 + }
25.799 +
25.800 + if (this.AbsoluteMaximum <= this.AbsoluteMinimum)
25.801 + {
25.802 + throw new InvalidOperationException("AbsoluteMaximum should be larger than AbsoluteMinimum.");
25.803 + }
25.804 + }
25.805 +
25.806 + /// <summary>
25.807 + /// Formats the value to be used on the axis.
25.808 + /// </summary>
25.809 + /// <param name="x">
25.810 + /// The value.
25.811 + /// </param>
25.812 + /// <returns>
25.813 + /// The formatted value.
25.814 + /// </returns>
25.815 + public virtual string FormatValue(double x)
25.816 + {
25.817 + // The "SuperExponentialFormat" renders the number with superscript exponents. E.g. 10^2
25.818 + if (this.UseSuperExponentialFormat)
25.819 + {
25.820 + // if (x == 1 || x == 10 || x == -1 || x == -10)
25.821 + // return x.ToString();
25.822 + double exp = Exponent(x);
25.823 + double mantissa = Mantissa(x);
25.824 + string fmt;
25.825 + if (this.StringFormat == null)
25.826 + {
25.827 + fmt = Math.Abs(mantissa - 1.0) < 1e-6 ? "10^{{{1:0}}}" : "{0}·10^{{{1:0}}}";
25.828 + }
25.829 + else
25.830 + {
25.831 + fmt = "{0:" + this.StringFormat + "}·10^{{{1:0}}}";
25.832 + }
25.833 +
25.834 + return string.Format(this.ActualCulture, fmt, mantissa, exp);
25.835 + }
25.836 +
25.837 + string format = this.ActualStringFormat ?? this.StringFormat ?? string.Empty;
25.838 + return x.ToString(format, this.ActualCulture);
25.839 + }
25.840 +
25.841 + /// <summary>
25.842 + /// Formats the value to be used by the tracker.
25.843 + /// </summary>
25.844 + /// <param name="x">
25.845 + /// The value.
25.846 + /// </param>
25.847 + /// <returns>
25.848 + /// The formatted value.
25.849 + /// </returns>
25.850 + public virtual string FormatValueForTracker(double x)
25.851 + {
25.852 + return x.ToString(this.ActualCulture);
25.853 + }
25.854 +
25.855 + /// <summary>
25.856 + /// Gets the coordinates used to draw ticks and tick labels (numbers or category names).
25.857 + /// </summary>
25.858 + /// <param name="majorLabelValues">
25.859 + /// The major label values.
25.860 + /// </param>
25.861 + /// <param name="majorTickValues">
25.862 + /// The major tick values.
25.863 + /// </param>
25.864 + /// <param name="minorTickValues">
25.865 + /// The minor tick values.
25.866 + /// </param>
25.867 + public virtual void GetTickValues(
25.868 + out IList<double> majorLabelValues, out IList<double> majorTickValues, out IList<double> minorTickValues)
25.869 + {
25.870 + minorTickValues = CreateTickValues(this.ActualMinimum, this.ActualMaximum, this.ActualMinorStep);
25.871 + majorTickValues = CreateTickValues(this.ActualMinimum, this.ActualMaximum, this.ActualMajorStep);
25.872 + majorLabelValues = majorTickValues;
25.873 + }
25.874 +
25.875 + /// <summary>
25.876 + /// Gets the value from an axis coordinate, converts from double to the correct data type if necessary. e.g. DateTimeAxis returns the DateTime and CategoryAxis returns category strings.
25.877 + /// </summary>
25.878 + /// <param name="x">
25.879 + /// The coordinate.
25.880 + /// </param>
25.881 + /// <returns>
25.882 + /// The value.
25.883 + /// </returns>
25.884 + public virtual object GetValue(double x)
25.885 + {
25.886 + return x;
25.887 + }
25.888 +
25.889 + /// <summary>
25.890 + /// Inverse transform the specified screen point.
25.891 + /// </summary>
25.892 + /// <param name="x">
25.893 + /// The x coordinate.
25.894 + /// </param>
25.895 + /// <param name="y">
25.896 + /// The y coordinate.
25.897 + /// </param>
25.898 + /// <param name="yaxis">
25.899 + /// The y-axis.
25.900 + /// </param>
25.901 + /// <returns>
25.902 + /// The data point.
25.903 + /// </returns>
25.904 + public virtual DataPoint InverseTransform(double x, double y, Axis yaxis)
25.905 + {
25.906 + return new DataPoint(this.InverseTransform(x), yaxis != null ? yaxis.InverseTransform(y) : 0);
25.907 + }
25.908 +
25.909 + /// <summary>
25.910 + /// Inverse transform the specified screen coordinate. This method can only be used with non-polar coordinate systems.
25.911 + /// </summary>
25.912 + /// <param name="sx">
25.913 + /// The screen coordinate.
25.914 + /// </param>
25.915 + /// <returns>
25.916 + /// The value.
25.917 + /// </returns>
25.918 + public virtual double InverseTransform(double sx)
25.919 + {
25.920 + return this.PostInverseTransform((sx / this.scale) + this.offset);
25.921 + }
25.922 +
25.923 + /// <summary>
25.924 + /// Determines whether this axis is horizontal.
25.925 + /// </summary>
25.926 + /// <returns>
25.927 + /// <c>true</c> if this axis is horizontal; otherwise, <c>false</c> .
25.928 + /// </returns>
25.929 + public bool IsHorizontal()
25.930 + {
25.931 + return this.position == AxisPosition.Top || this.position == AxisPosition.Bottom;
25.932 + }
25.933 +
25.934 + /// <summary>
25.935 + /// Determines whether the specified value is valid.
25.936 + /// </summary>
25.937 + /// <param name="value">
25.938 + /// The value.
25.939 + /// </param>
25.940 + /// <returns>
25.941 + /// <c>true</c> if the specified value is valid; otherwise, <c>false</c> .
25.942 + /// </returns>
25.943 + public virtual bool IsValidValue(double value)
25.944 + {
25.945 + return !double.IsNaN(value) && !double.IsInfinity(value) && value < this.FilterMaxValue
25.946 + && value > this.FilterMinValue && (this.FilterFunction == null || this.FilterFunction(value));
25.947 + }
25.948 +
25.949 + /// <summary>
25.950 + /// Determines whether this axis is vertical.
25.951 + /// </summary>
25.952 + /// <returns>
25.953 + /// <c>true</c> if this axis is vertical; otherwise, <c>false</c> .
25.954 + /// </returns>
25.955 + public bool IsVertical()
25.956 + {
25.957 + return this.position == AxisPosition.Left || this.position == AxisPosition.Right;
25.958 + }
25.959 +
25.960 + /// <summary>
25.961 + /// Determines whether the axis is used for X/Y values.
25.962 + /// </summary>
25.963 + /// <returns>
25.964 + /// <c>true</c> if it is an XY axis; otherwise, <c>false</c> .
25.965 + /// </returns>
25.966 + public abstract bool IsXyAxis();
25.967 +
25.968 + /// <summary>
25.969 + /// Measures the size of the axis (maximum axis label width/height).
25.970 + /// </summary>
25.971 + /// <param name="rc">
25.972 + /// The render context.
25.973 + /// </param>
25.974 + /// <returns>
25.975 + /// The size of the axis.
25.976 + /// </returns>
25.977 + public virtual OxySize Measure(IRenderContext rc)
25.978 + {
25.979 + IList<double> majorTickValues;
25.980 + IList<double> minorTickValues;
25.981 + IList<double> majorLabelValues;
25.982 +
25.983 + this.GetTickValues(out majorLabelValues, out majorTickValues, out minorTickValues);
25.984 +
25.985 + var maximumTextSize = new OxySize();
25.986 + foreach (double v in majorLabelValues)
25.987 + {
25.988 + string s = this.FormatValue(v);
25.989 + var size = rc.MeasureText(s, this.ActualFont, this.ActualFontSize, this.ActualFontWeight);
25.990 + if (size.Width > maximumTextSize.Width)
25.991 + {
25.992 + maximumTextSize.Width = size.Width;
25.993 + }
25.994 +
25.995 + if (size.Height > maximumTextSize.Height)
25.996 + {
25.997 + maximumTextSize.Height = size.Height;
25.998 + }
25.999 + }
25.1000 +
25.1001 + var labelTextSize = rc.MeasureText(
25.1002 + this.ActualTitle, this.ActualFont, this.ActualFontSize, this.ActualFontWeight);
25.1003 +
25.1004 + double width = 0;
25.1005 + double height = 0;
25.1006 +
25.1007 + if (this.IsHorizontal())
25.1008 + {
25.1009 + switch (this.TickStyle)
25.1010 + {
25.1011 + case TickStyle.Outside:
25.1012 + height += this.MajorTickSize;
25.1013 + break;
25.1014 + case TickStyle.Crossing:
25.1015 + height += this.MajorTickSize * 0.75;
25.1016 + break;
25.1017 + }
25.1018 +
25.1019 + height += this.AxisTickToLabelDistance;
25.1020 + height += maximumTextSize.Height;
25.1021 + if (labelTextSize.Height > 0)
25.1022 + {
25.1023 + height += this.AxisTitleDistance;
25.1024 + height += labelTextSize.Height;
25.1025 + }
25.1026 + }
25.1027 + else
25.1028 + {
25.1029 + switch (this.TickStyle)
25.1030 + {
25.1031 + case TickStyle.Outside:
25.1032 + width += this.MajorTickSize;
25.1033 + break;
25.1034 + case TickStyle.Crossing:
25.1035 + width += this.MajorTickSize * 0.75;
25.1036 + break;
25.1037 + }
25.1038 +
25.1039 + width += this.AxisTickToLabelDistance;
25.1040 + width += maximumTextSize.Width;
25.1041 + if (labelTextSize.Height > 0)
25.1042 + {
25.1043 + width += this.AxisTitleDistance;
25.1044 + width += labelTextSize.Height;
25.1045 + }
25.1046 + }
25.1047 +
25.1048 + return new OxySize(width, height);
25.1049 + }
25.1050 +
25.1051 + /// <summary>
25.1052 + /// Pans the specified axis.
25.1053 + /// </summary>
25.1054 + /// <param name="ppt">
25.1055 + /// The previous point (screen coordinates).
25.1056 + /// </param>
25.1057 + /// <param name="cpt">
25.1058 + /// The current point (screen coordinates).
25.1059 + /// </param>
25.1060 + public virtual void Pan(ScreenPoint ppt, ScreenPoint cpt)
25.1061 + {
25.1062 + if (!this.IsPanEnabled)
25.1063 + {
25.1064 + return;
25.1065 + }
25.1066 +
25.1067 + bool isHorizontal = this.IsHorizontal();
25.1068 +
25.1069 + double dsx = isHorizontal ? cpt.X - ppt.X : cpt.Y - ppt.Y;
25.1070 + this.Pan(dsx);
25.1071 + }
25.1072 +
25.1073 + /// <summary>
25.1074 + /// Pans the specified axis.
25.1075 + /// </summary>
25.1076 + /// <param name="delta">
25.1077 + /// The delta.
25.1078 + /// </param>
25.1079 + public virtual void Pan(double delta)
25.1080 + {
25.1081 + if (!this.IsPanEnabled)
25.1082 + {
25.1083 + return;
25.1084 + }
25.1085 +
25.1086 + double dx = delta / this.Scale;
25.1087 +
25.1088 + double newMinimum = this.ActualMinimum - dx;
25.1089 + double newMaximum = this.ActualMaximum - dx;
25.1090 + if (newMinimum < this.AbsoluteMinimum)
25.1091 + {
25.1092 + newMinimum = this.AbsoluteMinimum;
25.1093 + newMaximum = newMinimum + this.ActualMaximum - this.ActualMinimum;
25.1094 + }
25.1095 +
25.1096 + if (newMaximum > this.AbsoluteMaximum)
25.1097 + {
25.1098 + newMaximum = this.AbsoluteMaximum;
25.1099 + newMinimum = newMaximum - (this.ActualMaximum - this.ActualMinimum);
25.1100 + }
25.1101 +
25.1102 + this.ViewMinimum = newMinimum;
25.1103 + this.ViewMaximum = newMaximum;
25.1104 + this.UpdateActualMaxMin();
25.1105 +
25.1106 + this.OnAxisChanged(new AxisChangedEventArgs(AxisChangeTypes.Pan));
25.1107 + }
25.1108 +
25.1109 + /// <summary>
25.1110 + /// Renders the axis on the specified render context.
25.1111 + /// </summary>
25.1112 + /// <param name="rc">The render context.</param>
25.1113 + /// <param name="model">The model.</param>
25.1114 + /// <param name="axisLayer">The rendering order.</param>
25.1115 + /// <param name="pass">The pass.</param>
25.1116 + public virtual void Render(IRenderContext rc, PlotModel model, AxisLayer axisLayer, int pass)
25.1117 + {
25.1118 + var r = new HorizontalAndVerticalAxisRenderer(rc, model);
25.1119 + r.Render(this, pass);
25.1120 + }
25.1121 +
25.1122 + /// <summary>
25.1123 + /// Resets the user's modification (zooming/panning) to minimum and maximum of this axis.
25.1124 + /// </summary>
25.1125 + public virtual void Reset()
25.1126 + {
25.1127 + this.ViewMinimum = double.NaN;
25.1128 + this.ViewMaximum = double.NaN;
25.1129 + this.UpdateActualMaxMin();
25.1130 + this.OnAxisChanged(new AxisChangedEventArgs(AxisChangeTypes.Reset));
25.1131 + }
25.1132 +
25.1133 + /// <summary>
25.1134 + /// Returns a <see cref="System.String"/> that represents this instance.
25.1135 + /// </summary>
25.1136 + /// <returns>
25.1137 + /// A <see cref="System.String"/> that represents this instance.
25.1138 + /// </returns>
25.1139 + public override string ToString()
25.1140 + {
25.1141 + return string.Format(
25.1142 + CultureInfo.InvariantCulture,
25.1143 + "{0}({1}, {2}, {3}, {4})",
25.1144 + this.GetType().Name,
25.1145 + this.Position,
25.1146 + this.ActualMinimum,
25.1147 + this.ActualMaximum,
25.1148 + this.ActualMajorStep);
25.1149 + }
25.1150 +
25.1151 + /// <summary>
25.1152 + /// Transforms the specified point to screen coordinates.
25.1153 + /// </summary>
25.1154 + /// <param name="x">
25.1155 + /// The x value (for the current axis).
25.1156 + /// </param>
25.1157 + /// <param name="y">
25.1158 + /// The y value.
25.1159 + /// </param>
25.1160 + /// <param name="yaxis">
25.1161 + /// The y axis.
25.1162 + /// </param>
25.1163 + /// <returns>
25.1164 + /// The transformed point.
25.1165 + /// </returns>
25.1166 + public virtual ScreenPoint Transform(double x, double y, Axis yaxis)
25.1167 + {
25.1168 + if (yaxis == null)
25.1169 + {
25.1170 + throw new NullReferenceException("Y axis should not be null when transforming.");
25.1171 + }
25.1172 +
25.1173 + return new ScreenPoint(this.Transform(x), yaxis.Transform(y));
25.1174 + }
25.1175 +
25.1176 + /// <summary>
25.1177 + /// Transforms the specified coordinate to screen coordinates. This method can only be used with non-polar coordinate systems.
25.1178 + /// </summary>
25.1179 + /// <param name="x">
25.1180 + /// The value.
25.1181 + /// </param>
25.1182 + /// <returns>
25.1183 + /// The transformed value (screen coordinate).
25.1184 + /// </returns>
25.1185 + public virtual double Transform(double x)
25.1186 + {
25.1187 + return (x - this.offset) * this.scale;
25.1188 +
25.1189 + // return (this.PreTransform(x) - this.Offset) * this.Scale;
25.1190 + }
25.1191 +
25.1192 + /// <summary>
25.1193 + /// Zoom to the specified scale.
25.1194 + /// </summary>
25.1195 + /// <param name="newScale">
25.1196 + /// The new scale.
25.1197 + /// </param>
25.1198 + public virtual void Zoom(double newScale)
25.1199 + {
25.1200 + double sx1 = this.Transform(this.ActualMaximum);
25.1201 + double sx0 = this.Transform(this.ActualMinimum);
25.1202 +
25.1203 + double sgn = Math.Sign(this.scale);
25.1204 + double mid = (this.ActualMaximum + this.ActualMinimum) / 2;
25.1205 +
25.1206 + double dx = (this.offset - mid) * this.scale;
25.1207 + this.scale = sgn * newScale;
25.1208 + this.offset = (dx / this.scale) + mid;
25.1209 +
25.1210 + double newMaximum = this.InverseTransform(sx1);
25.1211 + double newMinimum = this.InverseTransform(sx0);
25.1212 +
25.1213 + if (newMinimum < this.AbsoluteMinimum && newMaximum > this.AbsoluteMaximum)
25.1214 + {
25.1215 + newMinimum = this.AbsoluteMinimum;
25.1216 + newMaximum = this.AbsoluteMaximum;
25.1217 + }
25.1218 + else
25.1219 + {
25.1220 + if (newMinimum < this.AbsoluteMinimum)
25.1221 + {
25.1222 + double d = newMaximum - newMinimum;
25.1223 + newMinimum = this.AbsoluteMinimum;
25.1224 + newMaximum = this.AbsoluteMinimum + d;
25.1225 + if (newMaximum > this.AbsoluteMaximum)
25.1226 + {
25.1227 + newMaximum = this.AbsoluteMaximum;
25.1228 + }
25.1229 + }
25.1230 + else if (newMaximum > this.AbsoluteMaximum)
25.1231 + {
25.1232 + double d = newMaximum - newMinimum;
25.1233 + newMaximum = this.AbsoluteMaximum;
25.1234 + newMinimum = this.AbsoluteMaximum - d;
25.1235 + if (newMinimum < this.AbsoluteMinimum)
25.1236 + {
25.1237 + newMinimum = this.AbsoluteMinimum;
25.1238 + }
25.1239 + }
25.1240 + }
25.1241 +
25.1242 + this.ViewMaximum = newMaximum;
25.1243 + this.ViewMinimum = newMinimum;
25.1244 + this.UpdateActualMaxMin();
25.1245 + }
25.1246 +
25.1247 + /// <summary>
25.1248 + /// Zooms the axis to the range [x0,x1].
25.1249 + /// </summary>
25.1250 + /// <param name="x0">
25.1251 + /// The new minimum.
25.1252 + /// </param>
25.1253 + /// <param name="x1">
25.1254 + /// The new maximum.
25.1255 + /// </param>
25.1256 + public virtual void Zoom(double x0, double x1)
25.1257 + {
25.1258 + if (!this.IsZoomEnabled)
25.1259 + {
25.1260 + return;
25.1261 + }
25.1262 +
25.1263 + double newMinimum = Math.Max(Math.Min(x0, x1), this.AbsoluteMinimum);
25.1264 + double newMaximum = Math.Min(Math.Max(x0, x1), this.AbsoluteMaximum);
25.1265 +
25.1266 + this.ViewMinimum = newMinimum;
25.1267 + this.ViewMaximum = newMaximum;
25.1268 + this.UpdateActualMaxMin();
25.1269 +
25.1270 + this.OnAxisChanged(new AxisChangedEventArgs(AxisChangeTypes.Zoom));
25.1271 + }
25.1272 +
25.1273 + /// <summary>
25.1274 + /// Zooms the axis at the specified coordinate.
25.1275 + /// </summary>
25.1276 + /// <param name="factor">
25.1277 + /// The zoom factor.
25.1278 + /// </param>
25.1279 + /// <param name="x">
25.1280 + /// The coordinate to zoom at.
25.1281 + /// </param>
25.1282 + public virtual void ZoomAt(double factor, double x)
25.1283 + {
25.1284 + if (!this.IsZoomEnabled)
25.1285 + {
25.1286 + return;
25.1287 + }
25.1288 +
25.1289 + double dx0 = (this.ActualMinimum - x) * this.scale;
25.1290 + double dx1 = (this.ActualMaximum - x) * this.scale;
25.1291 + this.scale *= factor;
25.1292 +
25.1293 + double newMinimum = Math.Max((dx0 / this.scale) + x, this.AbsoluteMinimum);
25.1294 + double newMaximum = Math.Min((dx1 / this.scale) + x, this.AbsoluteMaximum);
25.1295 +
25.1296 + this.ViewMinimum = newMinimum;
25.1297 + this.ViewMaximum = newMaximum;
25.1298 + this.UpdateActualMaxMin();
25.1299 +
25.1300 + this.OnAxisChanged(new AxisChangedEventArgs(AxisChangeTypes.Zoom));
25.1301 + }
25.1302 +
25.1303 + /// <summary>
25.1304 + /// Modifies the data range of the axis [DataMinimum,DataMaximum] to includes the specified value.
25.1305 + /// </summary>
25.1306 + /// <param name="value">
25.1307 + /// The value.
25.1308 + /// </param>
25.1309 + public virtual void Include(double value)
25.1310 + {
25.1311 + if (!this.IsValidValue(value))
25.1312 + {
25.1313 + return;
25.1314 + }
25.1315 +
25.1316 + this.DataMinimum = double.IsNaN(this.DataMinimum) ? value : Math.Min(this.DataMinimum, value);
25.1317 + this.DataMaximum = double.IsNaN(this.DataMaximum) ? value : Math.Max(this.DataMaximum, value);
25.1318 + }
25.1319 +
25.1320 + /// <summary>
25.1321 + /// Applies a transformation after the inverse transform of the value. This is used in logarithmic axis.
25.1322 + /// </summary>
25.1323 + /// <param name="x">
25.1324 + /// The value to transform.
25.1325 + /// </param>
25.1326 + /// <returns>
25.1327 + /// The transformed value.
25.1328 + /// </returns>
25.1329 + internal virtual double PostInverseTransform(double x)
25.1330 + {
25.1331 + return x;
25.1332 + }
25.1333 +
25.1334 + /// <summary>
25.1335 + /// Applies a transformation before the transform the value. This is used in logarithmic axis.
25.1336 + /// </summary>
25.1337 + /// <param name="x">
25.1338 + /// The value to transform.
25.1339 + /// </param>
25.1340 + /// <returns>
25.1341 + /// The transformed value.
25.1342 + /// </returns>
25.1343 + internal virtual double PreTransform(double x)
25.1344 + {
25.1345 + return x;
25.1346 + }
25.1347 +
25.1348 + /// <summary>
25.1349 + /// Resets the data maximum and minimum.
25.1350 + /// </summary>
25.1351 + internal virtual void ResetDataMaxMin()
25.1352 + {
25.1353 + this.DataMaximum = this.DataMinimum = double.NaN;
25.1354 + }
25.1355 +
25.1356 + /// <summary>
25.1357 + /// Updates the actual maximum and minimum values. If the user has zoomed/panned the axis, the internal ViewMaximum/ViewMinimum values will be used. If Maximum or Minimum have been set, these values will be used. Otherwise the maximum and minimum values of the series will be used, including the 'padding'.
25.1358 + /// </summary>
25.1359 + internal virtual void UpdateActualMaxMin()
25.1360 + {
25.1361 + // Use the minimum/maximum of the data as default
25.1362 + this.ActualMaximum = this.DataMaximum;
25.1363 + this.ActualMinimum = this.DataMinimum;
25.1364 +
25.1365 + double range = this.ActualMaximum - this.ActualMinimum;
25.1366 + double zeroRange = this.ActualMaximum > 0 ? this.ActualMaximum : 1;
25.1367 +
25.1368 + if (!double.IsNaN(this.ViewMaximum))
25.1369 + {
25.1370 + // Override the ActualMaximum by the ViewMaximum value (from zoom/pan)
25.1371 + this.ActualMaximum = this.ViewMaximum;
25.1372 + }
25.1373 + else if (!double.IsNaN(this.Maximum))
25.1374 + {
25.1375 + // Override the ActualMaximum by the Maximum value
25.1376 + this.ActualMaximum = this.Maximum;
25.1377 + }
25.1378 + else
25.1379 + {
25.1380 + if (range < double.Epsilon)
25.1381 + {
25.1382 + this.ActualMaximum += zeroRange * 0.5;
25.1383 + }
25.1384 +
25.1385 + if (!double.IsNaN(this.ActualMinimum) && !double.IsNaN(this.ActualMaximum))
25.1386 + {
25.1387 + double x1 = this.PreTransform(this.ActualMaximum);
25.1388 + double x0 = this.PreTransform(this.ActualMinimum);
25.1389 + double dx = this.MaximumPadding * (x1 - x0);
25.1390 + this.ActualMaximum = this.PostInverseTransform(x1 + dx);
25.1391 + }
25.1392 + }
25.1393 +
25.1394 + if (!double.IsNaN(this.ViewMinimum))
25.1395 + {
25.1396 + this.ActualMinimum = this.ViewMinimum;
25.1397 + }
25.1398 + else if (!double.IsNaN(this.Minimum))
25.1399 + {
25.1400 + this.ActualMinimum = this.Minimum;
25.1401 + }
25.1402 + else
25.1403 + {
25.1404 + if (range < double.Epsilon)
25.1405 + {
25.1406 + this.ActualMinimum -= zeroRange * 0.5;
25.1407 + }
25.1408 +
25.1409 + if (!double.IsNaN(this.ActualMaximum) && !double.IsNaN(this.ActualMaximum))
25.1410 + {
25.1411 + double x1 = this.PreTransform(this.ActualMaximum);
25.1412 + double x0 = this.PreTransform(this.ActualMinimum);
25.1413 + double dx = this.MinimumPadding * (x1 - x0);
25.1414 + this.ActualMinimum = this.PostInverseTransform(x0 - dx);
25.1415 + }
25.1416 + }
25.1417 +
25.1418 + this.CoerceActualMaxMin();
25.1419 + }
25.1420 +
25.1421 + /// <summary>
25.1422 + /// Updates the axis with information from the plot series.
25.1423 + /// </summary>
25.1424 + /// <param name="series">
25.1425 + /// The series collection.
25.1426 + /// </param>
25.1427 + /// <remarks>
25.1428 + /// This is used by the category axis that need to know the number of series using the axis.
25.1429 + /// </remarks>
25.1430 + internal virtual void UpdateFromSeries(IEnumerable<Series> series)
25.1431 + {
25.1432 + }
25.1433 +
25.1434 + /// <summary>
25.1435 + /// Updates the actual minor and major step intervals.
25.1436 + /// </summary>
25.1437 + /// <param name="plotArea">
25.1438 + /// The plot area rectangle.
25.1439 + /// </param>
25.1440 + internal virtual void UpdateIntervals(OxyRect plotArea)
25.1441 + {
25.1442 + double labelSize = this.IntervalLength;
25.1443 + double length = this.IsHorizontal() ? plotArea.Width : plotArea.Height;
25.1444 + length *= Math.Abs(this.EndPosition - this.StartPosition);
25.1445 +
25.1446 + this.ActualMajorStep = !double.IsNaN(this.MajorStep)
25.1447 + ? this.MajorStep
25.1448 + : this.CalculateActualInterval(length, labelSize);
25.1449 +
25.1450 + this.ActualMinorStep = !double.IsNaN(this.MinorStep)
25.1451 + ? this.MinorStep
25.1452 + : this.CalculateMinorInterval(this.ActualMajorStep);
25.1453 +
25.1454 + if (double.IsNaN(this.ActualMinorStep))
25.1455 + {
25.1456 + this.ActualMinorStep = 2;
25.1457 + }
25.1458 +
25.1459 + if (double.IsNaN(this.ActualMajorStep))
25.1460 + {
25.1461 + this.ActualMajorStep = 10;
25.1462 + }
25.1463 +
25.1464 + this.ActualStringFormat = this.StringFormat;
25.1465 +
25.1466 + // if (ActualStringFormat==null)
25.1467 + // {
25.1468 + // if (ActualMaximum > 1e6 || ActualMinimum < 1e-6)
25.1469 + // ActualStringFormat = "#.#e-0";
25.1470 + // }
25.1471 + }
25.1472 +
25.1473 + /// <summary>
25.1474 + /// Updates the scale and offset properties of the transform from the specified boundary rectangle.
25.1475 + /// </summary>
25.1476 + /// <param name="bounds">
25.1477 + /// The bounds.
25.1478 + /// </param>
25.1479 + internal virtual void UpdateTransform(OxyRect bounds)
25.1480 + {
25.1481 + double x0 = bounds.Left;
25.1482 + double x1 = bounds.Right;
25.1483 + double y0 = bounds.Bottom;
25.1484 + double y1 = bounds.Top;
25.1485 +
25.1486 + this.ScreenMin = new ScreenPoint(x0, y1);
25.1487 + this.ScreenMax = new ScreenPoint(x1, y0);
25.1488 +
25.1489 + // this.MidPoint = new ScreenPoint((x0 + x1) / 2, (y0 + y1) / 2);
25.1490 +
25.1491 + // if (this.Position == AxisPosition.Angle)
25.1492 + // {
25.1493 + // this.scale = 2 * Math.PI / (this.ActualMaximum - this.ActualMinimum);
25.1494 + // this.Offset = this.ActualMinimum;
25.1495 + // return;
25.1496 + // }
25.1497 +
25.1498 + // if (this.Position == AxisPosition.Magnitude)
25.1499 + // {
25.1500 + // this.ActualMinimum = 0;
25.1501 + // double r = Math.Min(Math.Abs(x1 - x0), Math.Abs(y1 - y0));
25.1502 + // this.scale = 0.5 * r / (this.ActualMaximum - this.ActualMinimum);
25.1503 + // this.Offset = this.ActualMinimum;
25.1504 + // return;
25.1505 + // }
25.1506 + double a0 = this.IsHorizontal() ? x0 : y0;
25.1507 + double a1 = this.IsHorizontal() ? x1 : y1;
25.1508 +
25.1509 + double dx = a1 - a0;
25.1510 + a1 = a0 + (this.EndPosition * dx);
25.1511 + a0 = a0 + (this.StartPosition * dx);
25.1512 + this.ScreenMin = new ScreenPoint(a0, a1);
25.1513 + this.ScreenMax = new ScreenPoint(a1, a0);
25.1514 +
25.1515 + if (this.ActualMaximum - this.ActualMinimum < double.Epsilon)
25.1516 + {
25.1517 + this.ActualMaximum = this.ActualMinimum + 1;
25.1518 + }
25.1519 +
25.1520 + double max = this.PreTransform(this.ActualMaximum);
25.1521 + double min = this.PreTransform(this.ActualMinimum);
25.1522 +
25.1523 + double da = a0 - a1;
25.1524 + if (Math.Abs(da) > double.Epsilon)
25.1525 + {
25.1526 + this.offset = (a0 / da * max) - (a1 / da * min);
25.1527 + }
25.1528 + else
25.1529 + {
25.1530 + this.offset = 0;
25.1531 + }
25.1532 +
25.1533 + double range = max - min;
25.1534 + if (Math.Abs(range) > double.Epsilon)
25.1535 + {
25.1536 + this.scale = (a1 - a0) / range;
25.1537 + }
25.1538 + else
25.1539 + {
25.1540 + this.scale = 1;
25.1541 + }
25.1542 + }
25.1543 +
25.1544 + /// <summary>
25.1545 + /// Creates tick values at the specified interval.
25.1546 + /// </summary>
25.1547 + /// <param name="min">
25.1548 + /// The minimum coordinate.
25.1549 + /// </param>
25.1550 + /// <param name="max">
25.1551 + /// The maximum coordinate.
25.1552 + /// </param>
25.1553 + /// <param name="step">
25.1554 + /// The interval.
25.1555 + /// </param>
25.1556 + /// <returns>
25.1557 + /// A list of tick values.
25.1558 + /// </returns>
25.1559 + protected static IList<double> CreateTickValues(double min, double max, double step)
25.1560 + {
25.1561 + if (max <= min)
25.1562 + {
25.1563 + throw new ArgumentException("Axis: Maximum should be larger than minimum.", "max");
25.1564 + }
25.1565 +
25.1566 + if (step <= 0)
25.1567 + {
25.1568 + throw new ArgumentException("Axis: Step cannot be zero or negative.", "step");
25.1569 + }
25.1570 +
25.1571 + double x0 = Math.Round(min / step) * step;
25.1572 + int n = Math.Max((int)((max - min) / step), 1);
25.1573 + var values = new List<double>(n);
25.1574 +
25.1575 + // Limit the maximum number of iterations (in case something is wrong with the step size)
25.1576 + int i = 0;
25.1577 + const int MaxIterations = 1000;
25.1578 + double x = x0;
25.1579 + double eps = step * 1e-3;
25.1580 +
25.1581 + while (x <= max + eps && i < MaxIterations)
25.1582 + {
25.1583 + x = x0 + (i * step);
25.1584 + i++;
25.1585 + if (x >= min - eps && x <= max + eps)
25.1586 + {
25.1587 + x = x.RemoveNoise();
25.1588 + values.Add(x);
25.1589 + }
25.1590 + }
25.1591 +
25.1592 + return values;
25.1593 + }
25.1594 +
25.1595 + /// <summary>
25.1596 + /// Calculates the actual interval.
25.1597 + /// </summary>
25.1598 + /// <param name="availableSize">
25.1599 + /// Size of the available area.
25.1600 + /// </param>
25.1601 + /// <param name="maxIntervalSize">
25.1602 + /// Maximum length of the intervals.
25.1603 + /// </param>
25.1604 + /// <returns>
25.1605 + /// The calculate actual interval.
25.1606 + /// </returns>
25.1607 + protected virtual double CalculateActualInterval(double availableSize, double maxIntervalSize)
25.1608 + {
25.1609 + return this.CalculateActualInterval(availableSize, maxIntervalSize, this.ActualMaximum - this.ActualMinimum);
25.1610 + }
25.1611 +
25.1612 + // alternative algorithm not in use
25.1613 + /* private double CalculateActualIntervalOldAlgorithm(double availableSize, double maxIntervalSize)
25.1614 + {
25.1615 + const int minimumTags = 5;
25.1616 + const int maximumTags = 20;
25.1617 + var numberOfTags = (int) (availableSize/maxIntervalSize);
25.1618 + double range = ActualMaximum - ActualMinimum;
25.1619 + double interval = range/numberOfTags;
25.1620 + const int k1 = 10;
25.1621 + interval = Math.Log10(interval/k1);
25.1622 + interval = Math.Ceiling(interval);
25.1623 + interval = Math.Pow(10, interval)*k1;
25.1624 +
25.1625 + if (range/interval > maximumTags) interval *= 5;
25.1626 + if (range/interval < minimumTags) interval *= 0.5;
25.1627 +
25.1628 + if (interval <= 0) interval = 1;
25.1629 + return interval;
25.1630 + }*/
25.1631 +
25.1632 + // ===
25.1633 + // the following algorithm is from
25.1634 + // System.Windows.Controls.DataVisualization.Charting.LinearAxis.cs
25.1635 +
25.1636 + // (c) Copyright Microsoft Corporation.
25.1637 + // This source is subject to the Microsoft Public License (MIT).
25.1638 + // Please see http://go.microsoft.com/fwlink/?LinkID=131993 for details.
25.1639 + // All other rights reserved.
25.1640 +
25.1641 + /// <summary>
25.1642 + /// Returns the actual interval to use to determine which values are displayed in the axis.
25.1643 + /// </summary>
25.1644 + /// <param name="availableSize">
25.1645 + /// The available size.
25.1646 + /// </param>
25.1647 + /// <param name="maxIntervalSize">
25.1648 + /// The maximum interval size.
25.1649 + /// </param>
25.1650 + /// <param name="range">
25.1651 + /// The range.
25.1652 + /// </param>
25.1653 + /// <returns>
25.1654 + /// Actual interval to use to determine which values are displayed in the axis.
25.1655 + /// </returns>
25.1656 + protected double CalculateActualInterval(double availableSize, double maxIntervalSize, double range)
25.1657 + {
25.1658 + if (availableSize <= 0)
25.1659 + {
25.1660 + return maxIntervalSize;
25.1661 + }
25.1662 +
25.1663 + Func<double, double> exponent = x => Math.Ceiling(Math.Log(x, 10));
25.1664 + Func<double, double> mantissa = x => x / Math.Pow(10, exponent(x) - 1);
25.1665 +
25.1666 + // reduce intervals for horizontal axis.
25.1667 + // double maxIntervals = Orientation == AxisOrientation.x ? MaximumAxisIntervalsPer200Pixels * 0.8 : MaximumAxisIntervalsPer200Pixels;
25.1668 + // real maximum interval count
25.1669 + double maxIntervalCount = availableSize / maxIntervalSize;
25.1670 +
25.1671 + range = Math.Abs(range);
25.1672 + double interval = Math.Pow(10, exponent(range));
25.1673 + double tempInterval = interval;
25.1674 +
25.1675 + // decrease interval until interval count becomes less than maxIntervalCount
25.1676 + while (true)
25.1677 + {
25.1678 + var m = (int)mantissa(tempInterval);
25.1679 + if (m == 5)
25.1680 + {
25.1681 + // reduce 5 to 2
25.1682 + tempInterval = (tempInterval / 2.5).RemoveNoiseFromDoubleMath();
25.1683 + }
25.1684 + else if (m == 2 || m == 1 || m == 10)
25.1685 + {
25.1686 + // reduce 2 to 1, 10 to 5, 1 to 0.5
25.1687 + tempInterval = (tempInterval / 2.0).RemoveNoiseFromDoubleMath();
25.1688 + }
25.1689 + else
25.1690 + {
25.1691 + tempInterval = (tempInterval / 2.0).RemoveNoiseFromDoubleMath();
25.1692 + }
25.1693 +
25.1694 + if (range / tempInterval > maxIntervalCount)
25.1695 + {
25.1696 + break;
25.1697 + }
25.1698 +
25.1699 + if (double.IsNaN(tempInterval) || double.IsInfinity(tempInterval))
25.1700 + {
25.1701 + break;
25.1702 + }
25.1703 +
25.1704 + interval = tempInterval;
25.1705 + }
25.1706 +
25.1707 + return interval;
25.1708 + }
25.1709 +
25.1710 + /// <summary>
25.1711 + /// The calculate minor interval.
25.1712 + /// </summary>
25.1713 + /// <param name="majorInterval">
25.1714 + /// The major interval.
25.1715 + /// </param>
25.1716 + /// <returns>
25.1717 + /// The minor interval.
25.1718 + /// </returns>
25.1719 + protected double CalculateMinorInterval(double majorInterval)
25.1720 + {
25.1721 + // if major interval is 100, the minor interval will be 20.
25.1722 + return majorInterval / 5;
25.1723 +
25.1724 + // The following obsolete code divided major intervals into 4 minor intervals, unless the major interval's mantissa was 5.
25.1725 + // e.g. Major interval 100 => minor interval 25.
25.1726 +
25.1727 + // Func<double, double> exponent = x => Math.Ceiling(Math.Log(x, 10));
25.1728 + // Func<double, double> mantissa = x => x / Math.Pow(10, exponent(x) - 1);
25.1729 + // var m = (int)mantissa(majorInterval);
25.1730 + // switch (m)
25.1731 + // {
25.1732 + // case 5:
25.1733 + // return majorInterval / 5;
25.1734 + // default:
25.1735 + // return majorInterval / 4;
25.1736 + // }
25.1737 + }
25.1738 +
25.1739 + /// <summary>
25.1740 + /// Raises the AxisChanged event.
25.1741 + /// </summary>
25.1742 + /// <param name="args">
25.1743 + /// The <see cref="OxyPlot.Axes.AxisChangedEventArgs"/> instance containing the event data.
25.1744 + /// </param>
25.1745 + protected virtual void OnAxisChanged(AxisChangedEventArgs args)
25.1746 + {
25.1747 + this.UpdateActualMaxMin();
25.1748 +
25.1749 + var handler = this.AxisChanged;
25.1750 + if (handler != null)
25.1751 + {
25.1752 + handler(this, args);
25.1753 + }
25.1754 + }
25.1755 + }
25.1756 +}
25.1757 \ No newline at end of file
26.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
26.2 +++ b/External/OxyPlot/OxyPlot/Axes/AxisChangeTypes.cs Sat Jun 08 16:53:22 2013 +0000
26.3 @@ -0,0 +1,52 @@
26.4 +// --------------------------------------------------------------------------------------------------------------------
26.5 +// <copyright file="AxisChangeTypes.cs" company="OxyPlot">
26.6 +// The MIT License (MIT)
26.7 +//
26.8 +// Copyright (c) 2012 Oystein Bjorke
26.9 +//
26.10 +// Permission is hereby granted, free of charge, to any person obtaining a
26.11 +// copy of this software and associated documentation files (the
26.12 +// "Software"), to deal in the Software without restriction, including
26.13 +// without limitation the rights to use, copy, modify, merge, publish,
26.14 +// distribute, sublicense, and/or sell copies of the Software, and to
26.15 +// permit persons to whom the Software is furnished to do so, subject to
26.16 +// the following conditions:
26.17 +//
26.18 +// The above copyright notice and this permission notice shall be included
26.19 +// in all copies or substantial portions of the Software.
26.20 +//
26.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
26.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
26.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
26.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
26.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
26.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
26.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
26.28 +// </copyright>
26.29 +// <summary>
26.30 +// Change types of the Axis.AxisChanged event.
26.31 +// </summary>
26.32 +// --------------------------------------------------------------------------------------------------------------------
26.33 +namespace OxyPlot.Axes
26.34 +{
26.35 + /// <summary>
26.36 + /// Specifies change types for the <see cref="Axis.AxisChanged"/> event.
26.37 + /// </summary>
26.38 + public enum AxisChangeTypes
26.39 + {
26.40 + /// <summary>
26.41 + /// The axis was zoomed by the user.
26.42 + /// </summary>
26.43 + Zoom,
26.44 +
26.45 + /// <summary>
26.46 + /// The axis was panned by the user.
26.47 + /// </summary>
26.48 + Pan,
26.49 +
26.50 + /// <summary>
26.51 + /// The axis zoom/pan was reset by the user.
26.52 + /// </summary>
26.53 + Reset
26.54 + }
26.55 +}
26.56 \ No newline at end of file
27.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
27.2 +++ b/External/OxyPlot/OxyPlot/Axes/AxisChangedEventArgs.cs Sat Jun 08 16:53:22 2013 +0000
27.3 @@ -0,0 +1,57 @@
27.4 +// --------------------------------------------------------------------------------------------------------------------
27.5 +// <copyright file="AxisChangedEventArgs.cs" company="OxyPlot">
27.6 +// The MIT License (MIT)
27.7 +//
27.8 +// Copyright (c) 2012 Oystein Bjorke
27.9 +//
27.10 +// Permission is hereby granted, free of charge, to any person obtaining a
27.11 +// copy of this software and associated documentation files (the
27.12 +// "Software"), to deal in the Software without restriction, including
27.13 +// without limitation the rights to use, copy, modify, merge, publish,
27.14 +// distribute, sublicense, and/or sell copies of the Software, and to
27.15 +// permit persons to whom the Software is furnished to do so, subject to
27.16 +// the following conditions:
27.17 +//
27.18 +// The above copyright notice and this permission notice shall be included
27.19 +// in all copies or substantial portions of the Software.
27.20 +//
27.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
27.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
27.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
27.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
27.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
27.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
27.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
27.28 +// </copyright>
27.29 +// <summary>
27.30 +// EventArgs for the Axis.AxisChanged event.
27.31 +// </summary>
27.32 +// --------------------------------------------------------------------------------------------------------------------
27.33 +namespace OxyPlot.Axes
27.34 +{
27.35 + using System;
27.36 +
27.37 + /// <summary>
27.38 + /// Provides additional data for the <see cref="Axis.AxisChanged"/> event.
27.39 + /// </summary>
27.40 + public class AxisChangedEventArgs : EventArgs
27.41 + {
27.42 + /// <summary>
27.43 + /// Initializes a new instance of the <see cref="AxisChangedEventArgs"/> class.
27.44 + /// </summary>
27.45 + /// <param name="changeType">
27.46 + /// Type of the change.
27.47 + /// </param>
27.48 + public AxisChangedEventArgs(AxisChangeTypes changeType)
27.49 + {
27.50 + this.ChangeType = changeType;
27.51 + }
27.52 +
27.53 + /// <summary>
27.54 + /// Gets or sets the type of the change.
27.55 + /// </summary>
27.56 + /// <value>The type of the change.</value>
27.57 + public AxisChangeTypes ChangeType { get; set; }
27.58 +
27.59 + }
27.60 +}
27.61 \ No newline at end of file
28.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
28.2 +++ b/External/OxyPlot/OxyPlot/Axes/AxisLayer.cs Sat Jun 08 16:53:22 2013 +0000
28.3 @@ -0,0 +1,47 @@
28.4 +// --------------------------------------------------------------------------------------------------------------------
28.5 +// <copyright file="AxisLayer.cs" company="OxyPlot">
28.6 +// The MIT License (MIT)
28.7 +//
28.8 +// Copyright (c) 2012 Oystein Bjorke
28.9 +//
28.10 +// Permission is hereby granted, free of charge, to any person obtaining a
28.11 +// copy of this software and associated documentation files (the
28.12 +// "Software"), to deal in the Software without restriction, including
28.13 +// without limitation the rights to use, copy, modify, merge, publish,
28.14 +// distribute, sublicense, and/or sell copies of the Software, and to
28.15 +// permit persons to whom the Software is furnished to do so, subject to
28.16 +// the following conditions:
28.17 +//
28.18 +// The above copyright notice and this permission notice shall be included
28.19 +// in all copies or substantial portions of the Software.
28.20 +//
28.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
28.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
28.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
28.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
28.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
28.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
28.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
28.28 +// </copyright>
28.29 +// <summary>
28.30 +// Axis layer position.
28.31 +// </summary>
28.32 +// --------------------------------------------------------------------------------------------------------------------
28.33 +namespace OxyPlot.Axes
28.34 +{
28.35 + /// <summary>
28.36 + /// Specifies the layer position of an <see cref="Axis"/>.
28.37 + /// </summary>
28.38 + public enum AxisLayer
28.39 + {
28.40 + /// <summary>
28.41 + /// Below all series.
28.42 + /// </summary>
28.43 + BelowSeries,
28.44 +
28.45 + /// <summary>
28.46 + /// Above all series.
28.47 + /// </summary>
28.48 + AboveSeries
28.49 + }
28.50 +}
28.51 \ No newline at end of file
29.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
29.2 +++ b/External/OxyPlot/OxyPlot/Axes/AxisPosition.cs Sat Jun 08 16:53:22 2013 +0000
29.3 @@ -0,0 +1,62 @@
29.4 +// --------------------------------------------------------------------------------------------------------------------
29.5 +// <copyright file="AxisPosition.cs" company="OxyPlot">
29.6 +// The MIT License (MIT)
29.7 +//
29.8 +// Copyright (c) 2012 Oystein Bjorke
29.9 +//
29.10 +// Permission is hereby granted, free of charge, to any person obtaining a
29.11 +// copy of this software and associated documentation files (the
29.12 +// "Software"), to deal in the Software without restriction, including
29.13 +// without limitation the rights to use, copy, modify, merge, publish,
29.14 +// distribute, sublicense, and/or sell copies of the Software, and to
29.15 +// permit persons to whom the Software is furnished to do so, subject to
29.16 +// the following conditions:
29.17 +//
29.18 +// The above copyright notice and this permission notice shall be included
29.19 +// in all copies or substantial portions of the Software.
29.20 +//
29.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
29.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
29.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
29.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
29.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
29.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
29.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29.28 +// </copyright>
29.29 +// <summary>
29.30 +// Axis positions.
29.31 +// </summary>
29.32 +// --------------------------------------------------------------------------------------------------------------------
29.33 +namespace OxyPlot.Axes
29.34 +{
29.35 + /// <summary>
29.36 + /// Specifies the position of an <see cref="Axis"/>.
29.37 + /// </summary>
29.38 + public enum AxisPosition
29.39 + {
29.40 + /// <summary>
29.41 + /// No position.
29.42 + /// </summary>
29.43 + None,
29.44 +
29.45 + /// <summary>
29.46 + /// Left of the plot area.
29.47 + /// </summary>
29.48 + Left,
29.49 +
29.50 + /// <summary>
29.51 + /// Right of the plot area.
29.52 + /// </summary>
29.53 + Right,
29.54 +
29.55 + /// <summary>
29.56 + /// Top of the plot area.
29.57 + /// </summary>
29.58 + Top,
29.59 +
29.60 + /// <summary>
29.61 + /// Bottom of the plot area.
29.62 + /// </summary>
29.63 + Bottom
29.64 + }
29.65 +}
29.66 \ No newline at end of file
30.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
30.2 +++ b/External/OxyPlot/OxyPlot/Axes/CategoryAxis.cs Sat Jun 08 16:53:22 2013 +0000
30.3 @@ -0,0 +1,501 @@
30.4 +// --------------------------------------------------------------------------------------------------------------------
30.5 +// <copyright file="CategoryAxis.cs" company="OxyPlot">
30.6 +// The MIT License (MIT)
30.7 +//
30.8 +// Copyright (c) 2012 Oystein Bjorke
30.9 +//
30.10 +// Permission is hereby granted, free of charge, to any person obtaining a
30.11 +// copy of this software and associated documentation files (the
30.12 +// "Software"), to deal in the Software without restriction, including
30.13 +// without limitation the rights to use, copy, modify, merge, publish,
30.14 +// distribute, sublicense, and/or sell copies of the Software, and to
30.15 +// permit persons to whom the Software is furnished to do so, subject to
30.16 +// the following conditions:
30.17 +//
30.18 +// The above copyright notice and this permission notice shall be included
30.19 +// in all copies or substantial portions of the Software.
30.20 +//
30.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
30.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
30.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
30.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
30.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
30.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
30.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
30.28 +// </copyright>
30.29 +// <summary>
30.30 +// Represents a category axes.
30.31 +// </summary>
30.32 +// --------------------------------------------------------------------------------------------------------------------
30.33 +namespace OxyPlot.Axes
30.34 +{
30.35 + using System.Collections;
30.36 + using System.Collections.Generic;
30.37 + using System.Globalization;
30.38 + using System.Linq;
30.39 +
30.40 + using OxyPlot.Series;
30.41 +
30.42 + /// <summary>
30.43 + /// Represents a category axis.
30.44 + /// </summary>
30.45 + /// <remarks>
30.46 + /// The category axis is using the label collection indices as the coordinate. If you have 5 categories in the Labels collection, the categories will be placed at coordinates 0 to 4. The range of the axis will be from -0.5 to 4.5 (excl. padding).
30.47 + /// </remarks>
30.48 + public class CategoryAxis : LinearAxis
30.49 + {
30.50 + /// <summary>
30.51 + /// Initializes a new instance of the <see cref="CategoryAxis"/> class.
30.52 + /// </summary>
30.53 + public CategoryAxis()
30.54 + {
30.55 + this.Labels = new List<string>();
30.56 + this.TickStyle = TickStyle.Outside;
30.57 + this.Position = AxisPosition.Bottom;
30.58 + this.MinimumPadding = 0;
30.59 + this.MaximumPadding = 0;
30.60 + this.MajorStep = 1;
30.61 + this.GapWidth = 1;
30.62 + }
30.63 +
30.64 + /// <summary>
30.65 + /// Initializes a new instance of the <see cref="CategoryAxis"/> class.
30.66 + /// </summary>
30.67 + /// <param name="position">The position.</param>
30.68 + /// <param name="title">The title.</param>
30.69 + /// <param name="categories">The categories.</param>
30.70 + public CategoryAxis(AxisPosition position, string title = null, params string[] categories)
30.71 + : this(title, categories)
30.72 + {
30.73 + this.Position = position;
30.74 + }
30.75 +
30.76 + /// <summary>
30.77 + /// Initializes a new instance of the <see cref="CategoryAxis"/> class.
30.78 + /// </summary>
30.79 + /// <param name="title">
30.80 + /// The title.
30.81 + /// </param>
30.82 + /// <param name="categories">
30.83 + /// The categories.
30.84 + /// </param>
30.85 + public CategoryAxis(string title, params string[] categories)
30.86 + : this()
30.87 + {
30.88 + this.Title = title;
30.89 + if (categories != null)
30.90 + {
30.91 + foreach (var c in categories)
30.92 + {
30.93 + this.Labels.Add(c);
30.94 + }
30.95 + }
30.96 + }
30.97 +
30.98 + /// <summary>
30.99 + /// Gets or sets the gap width.
30.100 + /// </summary>
30.101 + /// <remarks>
30.102 + /// The default value is 1.0 (100%). The gap width is given as a fraction of the total width/height of the items in a category.
30.103 + /// </remarks>
30.104 + public double GapWidth { get; set; }
30.105 +
30.106 + /// <summary>
30.107 + /// Gets or sets a value indicating whether the ticks are centered. If this is false, ticks will be drawn between each category. If this is true, ticks will be drawn in the middle of each category.
30.108 + /// </summary>
30.109 + public bool IsTickCentered { get; set; }
30.110 +
30.111 + /// <summary>
30.112 + /// Gets or sets the items source (used to update the Labels collection).
30.113 + /// </summary>
30.114 + /// <value>
30.115 + /// The items source.
30.116 + /// </value>
30.117 + public IEnumerable ItemsSource { get; set; }
30.118 +
30.119 + /// <summary>
30.120 + /// Gets or sets the data field for the labels.
30.121 + /// </summary>
30.122 + public string LabelField { get; set; }
30.123 +
30.124 + /// <summary>
30.125 + /// Gets or sets the labels collection.
30.126 + /// </summary>
30.127 + public IList<string> Labels { get; set; }
30.128 +
30.129 + /// <summary>
30.130 + /// Gets or sets the current offset of the bars (not used for stacked bar series).
30.131 + /// </summary>
30.132 + internal double[] BarOffset { get; set; }
30.133 +
30.134 + /// <summary>
30.135 + /// Gets or sets the max value per StackIndex and Label (only used for stacked bar series).
30.136 + /// </summary>
30.137 + internal double[,] MaxValue { get; set; }
30.138 +
30.139 + /// <summary>
30.140 + /// Gets or sets the maximal width of all labels
30.141 + /// </summary>
30.142 + internal double MaxWidth { get; set; }
30.143 +
30.144 + /// <summary>
30.145 + /// Gets or sets the min value per StackIndex and Label (only used for stacked bar series).
30.146 + /// </summary>
30.147 + internal double[,] MinValue { get; set; }
30.148 +
30.149 + /// <summary>
30.150 + /// Gets or sets per StackIndex and Label the base value for negative values of stacked bar series.
30.151 + /// </summary>
30.152 + internal double[,] NegativeBaseValues { get; set; }
30.153 +
30.154 + /// <summary>
30.155 + /// Gets or sets per StackIndex and Label the base value for positive values of stacked bar series.
30.156 + /// </summary>
30.157 + internal double[,] PositiveBaseValues { get; set; }
30.158 +
30.159 + /// <summary>
30.160 + /// Gets or sets the StackIndexMapping. The mapping indicates to which rank a specific stack index belongs.
30.161 + /// </summary>
30.162 + internal Dictionary<string, int> StackIndexMapping { get; set; }
30.163 +
30.164 + /// <summary>
30.165 + /// Gets or sets the offset of the bars per StackIndex and Label (only used for stacked bar series).
30.166 + /// </summary>
30.167 + internal double[,] StackedBarOffset { get; set; }
30.168 +
30.169 + /// <summary>
30.170 + /// Gets or sets sum of the widths of the single bars per label. This is used to find the bar width of BarSeries
30.171 + /// </summary>
30.172 + internal double[] TotalWidthPerCategory { get; set; }
30.173 +
30.174 + /// <summary>
30.175 + /// Fills the specified array.
30.176 + /// </summary>
30.177 + /// <param name="array">
30.178 + /// The array.
30.179 + /// </param>
30.180 + /// <param name="value">
30.181 + /// The value.
30.182 + /// </param>
30.183 + public static void Fill(double[] array, double value)
30.184 + {
30.185 + for (var i = 0; i < array.Length; i++)
30.186 + {
30.187 + array[i] = value;
30.188 + }
30.189 + }
30.190 +
30.191 + /// <summary>
30.192 + /// Fills the specified array.
30.193 + /// </summary>
30.194 + /// <param name="array">
30.195 + /// The array.
30.196 + /// </param>
30.197 + /// <param name="value">
30.198 + /// The value.
30.199 + /// </param>
30.200 + public static void Fill(double[,] array, double value)
30.201 + {
30.202 + for (var i = 0; i < array.GetLength(0); i++)
30.203 + {
30.204 + for (var j = 0; j < array.GetLength(1); j++)
30.205 + {
30.206 + array[i, j] = value;
30.207 + }
30.208 + }
30.209 + }
30.210 +
30.211 + /// <summary>
30.212 + /// Formats the value to be used on the axis.
30.213 + /// </summary>
30.214 + /// <param name="x">
30.215 + /// The value.
30.216 + /// </param>
30.217 + /// <returns>
30.218 + /// The formatted value.
30.219 + /// </returns>
30.220 + public override string FormatValue(double x)
30.221 + {
30.222 + var index = (int)x;
30.223 + if (this.Labels != null && index >= 0 && index < this.Labels.Count)
30.224 + {
30.225 + return this.Labels[index];
30.226 + }
30.227 +
30.228 + return null;
30.229 + }
30.230 +
30.231 + /// <summary>
30.232 + /// Formats the value to be used by the tracker.
30.233 + /// </summary>
30.234 + /// <param name="x">
30.235 + /// The value.
30.236 + /// </param>
30.237 + /// <returns>
30.238 + /// The formatted value.
30.239 + /// </returns>
30.240 + public override string FormatValueForTracker(double x)
30.241 + {
30.242 + return this.FormatValue(x);
30.243 + }
30.244 +
30.245 + /// <summary>
30.246 + /// Gets the category value.
30.247 + /// </summary>
30.248 + /// <param name="categoryIndex">
30.249 + /// Index of the category.
30.250 + /// </param>
30.251 + /// <param name="stackIndex">
30.252 + /// Index of the stack.
30.253 + /// </param>
30.254 + /// <param name="actualBarWidth">
30.255 + /// Actual width of the bar.
30.256 + /// </param>
30.257 + /// <returns>
30.258 + /// The get category value.
30.259 + /// </returns>
30.260 + public double GetCategoryValue(int categoryIndex, int stackIndex, double actualBarWidth)
30.261 + {
30.262 + var offsetBegin = this.StackedBarOffset[stackIndex, categoryIndex];
30.263 + var offsetEnd = this.StackedBarOffset[stackIndex + 1, categoryIndex];
30.264 + return categoryIndex - 0.5 + ((offsetEnd + offsetBegin - actualBarWidth) * 0.5);
30.265 + }
30.266 +
30.267 + /// <summary>
30.268 + /// Gets the category value.
30.269 + /// </summary>
30.270 + /// <param name="categoryIndex">
30.271 + /// Index of the category.
30.272 + /// </param>
30.273 + /// <returns>
30.274 + /// The get category value.
30.275 + /// </returns>
30.276 + public double GetCategoryValue(int categoryIndex)
30.277 + {
30.278 + return categoryIndex - 0.5 + this.BarOffset[categoryIndex];
30.279 + }
30.280 +
30.281 + /// <summary>
30.282 + /// Gets the coordinates used to draw ticks and tick labels (numbers or category names).
30.283 + /// </summary>
30.284 + /// <param name="majorLabelValues">
30.285 + /// The major label values.
30.286 + /// </param>
30.287 + /// <param name="majorTickValues">
30.288 + /// The major tick values.
30.289 + /// </param>
30.290 + /// <param name="minorTickValues">
30.291 + /// The minor tick values.
30.292 + /// </param>
30.293 + public override void GetTickValues(
30.294 + out IList<double> majorLabelValues, out IList<double> majorTickValues, out IList<double> minorTickValues)
30.295 + {
30.296 + base.GetTickValues(out majorLabelValues, out majorTickValues, out minorTickValues);
30.297 + minorTickValues.Clear();
30.298 +
30.299 + if (!this.IsTickCentered)
30.300 + {
30.301 + // Subtract 0.5 from the label values to get the tick values.
30.302 + // Add one extra tick at the end.
30.303 + var mv = new List<double>(majorLabelValues.Count);
30.304 + mv.AddRange(majorLabelValues.Select(v => v - 0.5));
30.305 + if (mv.Count > 0)
30.306 + {
30.307 + mv.Add(mv[mv.Count - 1] + 1);
30.308 + }
30.309 +
30.310 + majorTickValues = mv;
30.311 + }
30.312 + }
30.313 +
30.314 + /// <summary>
30.315 + /// Gets the value from an axis coordinate, converts from double to the correct data type if necessary. e.g. DateTimeAxis returns the DateTime and CategoryAxis returns category strings.
30.316 + /// </summary>
30.317 + /// <param name="x">
30.318 + /// The coordinate.
30.319 + /// </param>
30.320 + /// <returns>
30.321 + /// The value.
30.322 + /// </returns>
30.323 + public override object GetValue(double x)
30.324 + {
30.325 + return this.FormatValue(x);
30.326 + }
30.327 +
30.328 + /// <summary>
30.329 + /// Updates the actual maximum and minimum values. If the user has zoomed/panned the axis, the internal ViewMaximum/ViewMinimum values will be used. If Maximum or Minimum have been set, these values will be used. Otherwise the maximum and minimum values of the series will be used, including the 'padding'.
30.330 + /// </summary>
30.331 + internal override void UpdateActualMaxMin()
30.332 + {
30.333 + // Update the DataMinimum/DataMaximum from the number of categories
30.334 + this.Include(-0.5);
30.335 +
30.336 + if (this.Labels != null && this.Labels.Count > 0)
30.337 + {
30.338 + this.Include((this.Labels.Count - 1) + 0.5);
30.339 + }
30.340 + else
30.341 + {
30.342 + this.Include(0.5);
30.343 + }
30.344 +
30.345 + base.UpdateActualMaxMin();
30.346 +
30.347 + this.MinorStep = 1;
30.348 + }
30.349 +
30.350 + /// <summary>
30.351 + /// Updates the axis with information from the plot series.
30.352 + /// </summary>
30.353 + /// <param name="series">
30.354 + /// The series collection.
30.355 + /// </param>
30.356 + /// <remarks>
30.357 + /// This is used by the category axis that need to know the number of series using the axis.
30.358 + /// </remarks>
30.359 + internal override void UpdateFromSeries(IEnumerable<Series> series)
30.360 + {
30.361 + if (this.Labels.Count == 0)
30.362 + {
30.363 + this.TotalWidthPerCategory = null;
30.364 + this.MaxWidth = double.NaN;
30.365 + this.BarOffset = null;
30.366 + this.StackedBarOffset = null;
30.367 + this.StackIndexMapping = null;
30.368 + this.PositiveBaseValues = null;
30.369 + this.NegativeBaseValues = null;
30.370 + this.MaxValue = null;
30.371 + this.MinValue = null;
30.372 +
30.373 + return;
30.374 + }
30.375 +
30.376 + this.TotalWidthPerCategory = new double[this.Labels.Count];
30.377 +
30.378 + var usedSeries = series.Where(s => s.IsUsing(this)).ToList();
30.379 +
30.380 + // Add width of stacked series
30.381 + var categorizedSeries = usedSeries.OfType<CategorizedSeries>().ToList();
30.382 + var stackedSeries = categorizedSeries.OfType<IStackableSeries>().Where(s => s.IsStacked).ToList();
30.383 + var stackIndices = stackedSeries.Select(s => s.StackGroup).Distinct().ToList();
30.384 + var stackRankBarWidth = new Dictionary<int, double>();
30.385 + for (var j = 0; j < stackIndices.Count; j++)
30.386 + {
30.387 + var maxBarWidth =
30.388 + stackedSeries.Where(s => s.StackGroup == stackIndices[j]).Select(
30.389 + s => ((CategorizedSeries)s).GetBarWidth()).Concat(new[] { 0.0 }).Max();
30.390 + for (var i = 0; i < this.Labels.Count; i++)
30.391 + {
30.392 + int k = 0;
30.393 + if (
30.394 + stackedSeries.SelectMany(s => ((CategorizedSeries)s).GetItems()).Any(
30.395 + item => item.GetCategoryIndex(k++) == i))
30.396 + {
30.397 + this.TotalWidthPerCategory[i] += maxBarWidth;
30.398 + }
30.399 + }
30.400 +
30.401 + stackRankBarWidth[j] = maxBarWidth;
30.402 + }
30.403 +
30.404 + // Add width of unstacked series
30.405 + var unstackedBarSeries =
30.406 + categorizedSeries.Where(s => !(s is IStackableSeries) || !((IStackableSeries)s).IsStacked).ToList();
30.407 + foreach (var s in unstackedBarSeries)
30.408 + {
30.409 + for (var i = 0; i < this.Labels.Count; i++)
30.410 + {
30.411 + int j = 0;
30.412 + var numberOfItems = s.GetItems().Count(item => item.GetCategoryIndex(j++) == i);
30.413 + this.TotalWidthPerCategory[i] += s.GetBarWidth() * numberOfItems;
30.414 + }
30.415 + }
30.416 +
30.417 + this.MaxWidth = this.TotalWidthPerCategory.Max();
30.418 +
30.419 + // Calculate BarOffset and StackedBarOffset
30.420 + this.BarOffset = new double[this.Labels.Count];
30.421 + this.StackedBarOffset = new double[stackIndices.Count + 1, this.Labels.Count];
30.422 +
30.423 + var factor = 0.5 / (1 + this.GapWidth) / this.MaxWidth;
30.424 + for (var i = 0; i < this.Labels.Count; i++)
30.425 + {
30.426 + this.BarOffset[i] = 0.5 - (this.TotalWidthPerCategory[i] * factor);
30.427 + }
30.428 +
30.429 + for (var j = 0; j <= stackIndices.Count; j++)
30.430 + {
30.431 + for (var i = 0; i < this.Labels.Count; i++)
30.432 + {
30.433 + int k = 0;
30.434 + if (
30.435 + stackedSeries.SelectMany(s => ((CategorizedSeries)s).GetItems()).All(
30.436 + item => item.GetCategoryIndex(k++) != i))
30.437 + {
30.438 + continue;
30.439 + }
30.440 +
30.441 + this.StackedBarOffset[j, i] = this.BarOffset[i];
30.442 + if (j < stackIndices.Count)
30.443 + {
30.444 + this.BarOffset[i] += stackRankBarWidth[j] / (1 + this.GapWidth) / this.MaxWidth;
30.445 + }
30.446 + }
30.447 + }
30.448 +
30.449 + stackIndices.Sort();
30.450 + this.StackIndexMapping = new Dictionary<string, int>();
30.451 + for (var i = 0; i < stackIndices.Count; i++)
30.452 + {
30.453 + this.StackIndexMapping.Add(stackIndices[i], i);
30.454 + }
30.455 +
30.456 + this.PositiveBaseValues = new double[stackIndices.Count, this.Labels.Count];
30.457 + Fill(this.PositiveBaseValues, double.NaN);
30.458 + this.NegativeBaseValues = new double[stackIndices.Count, this.Labels.Count];
30.459 + Fill(this.NegativeBaseValues, double.NaN);
30.460 +
30.461 + this.MaxValue = new double[stackIndices.Count, this.Labels.Count];
30.462 + Fill(this.MaxValue, double.NaN);
30.463 + this.MinValue = new double[stackIndices.Count, this.Labels.Count];
30.464 + Fill(this.MinValue, double.NaN);
30.465 + }
30.466 +
30.467 + /// <summary>
30.468 + /// Creates Labels list if no labels were set
30.469 + /// </summary>
30.470 + /// <param name="series">
30.471 + /// The list of series which are rendered
30.472 + /// </param>
30.473 + internal void UpdateLabels(IEnumerable<Series> series)
30.474 + {
30.475 + if (this.ItemsSource != null)
30.476 + {
30.477 + this.Labels.Clear();
30.478 + ReflectionHelper.FillList(this.ItemsSource, this.LabelField, this.Labels);
30.479 + }
30.480 +
30.481 + if (this.Labels.Count == 0)
30.482 + {
30.483 + foreach (var s in series)
30.484 + {
30.485 + if (!s.IsUsing(this))
30.486 + {
30.487 + continue;
30.488 + }
30.489 +
30.490 + var bsb = s as CategorizedSeries;
30.491 + if (bsb != null)
30.492 + {
30.493 + int max = bsb.GetItems().Count;
30.494 + while (this.Labels.Count < max)
30.495 + {
30.496 + this.Labels.Add((this.Labels.Count + 1).ToString(CultureInfo.InvariantCulture));
30.497 + }
30.498 + }
30.499 + }
30.500 + }
30.501 + }
30.502 +
30.503 + }
30.504 +}
30.505 \ No newline at end of file
31.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
31.2 +++ b/External/OxyPlot/OxyPlot/Axes/ColorAxis.cs Sat Jun 08 16:53:22 2013 +0000
31.3 @@ -0,0 +1,283 @@
31.4 +// --------------------------------------------------------------------------------------------------------------------
31.5 +// <copyright file="ColorAxis.cs" company="OxyPlot">
31.6 +// The MIT License (MIT)
31.7 +//
31.8 +// Copyright (c) 2012 Oystein Bjorke
31.9 +//
31.10 +// Permission is hereby granted, free of charge, to any person obtaining a
31.11 +// copy of this software and associated documentation files (the
31.12 +// "Software"), to deal in the Software without restriction, including
31.13 +// without limitation the rights to use, copy, modify, merge, publish,
31.14 +// distribute, sublicense, and/or sell copies of the Software, and to
31.15 +// permit persons to whom the Software is furnished to do so, subject to
31.16 +// the following conditions:
31.17 +//
31.18 +// The above copyright notice and this permission notice shall be included
31.19 +// in all copies or substantial portions of the Software.
31.20 +//
31.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
31.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
31.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
31.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
31.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
31.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
31.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
31.28 +// </copyright>
31.29 +// <summary>
31.30 +// The color axis.
31.31 +// </summary>
31.32 +// --------------------------------------------------------------------------------------------------------------------
31.33 +namespace OxyPlot.Axes
31.34 +{
31.35 + using System;
31.36 + using System.Collections.Generic;
31.37 +
31.38 + /// <summary>
31.39 + /// Represents a color axis.
31.40 + /// </summary>
31.41 + public class ColorAxis : Axis
31.42 + {
31.43 + /// <summary>
31.44 + /// Initializes a new instance of the <see cref="ColorAxis"/> class.
31.45 + /// </summary>
31.46 + public ColorAxis()
31.47 + {
31.48 + this.Position = AxisPosition.None;
31.49 + this.IsPanEnabled = false;
31.50 + this.IsZoomEnabled = false;
31.51 + }
31.52 +
31.53 + /// <summary>
31.54 + /// Gets or sets the color of values above the maximum value.
31.55 + /// </summary>
31.56 + /// <value> The color of the high values. </value>
31.57 + public OxyColor HighColor { get; set; }
31.58 +
31.59 + /// <summary>
31.60 + /// Gets or sets the color of values below the minimum value.
31.61 + /// </summary>
31.62 + /// <value> The color of the low values. </value>
31.63 + public OxyColor LowColor { get; set; }
31.64 +
31.65 + /// <summary>
31.66 + /// Gets or sets the palette.
31.67 + /// </summary>
31.68 + /// <value> The palette. </value>
31.69 + public OxyPalette Palette { get; set; }
31.70 +
31.71 + /// <summary>
31.72 + /// Gets the color.
31.73 + /// </summary>
31.74 + /// <param name="paletteIndex">
31.75 + /// The color map index (less than NumberOfEntries).
31.76 + /// </param>
31.77 + /// <returns>
31.78 + /// The color.
31.79 + /// </returns>
31.80 + public OxyColor GetColor(int paletteIndex)
31.81 + {
31.82 + if (paletteIndex == 0)
31.83 + {
31.84 + return this.LowColor;
31.85 + }
31.86 +
31.87 + if (paletteIndex == this.Palette.Colors.Count + 1)
31.88 + {
31.89 + return this.HighColor;
31.90 + }
31.91 +
31.92 + return this.Palette.Colors[paletteIndex - 1];
31.93 + }
31.94 +
31.95 + /// <summary>
31.96 + /// Gets the color for the specified value.
31.97 + /// </summary>
31.98 + /// <param name="value">
31.99 + /// The value.
31.100 + /// </param>
31.101 + /// <returns>
31.102 + /// The color.
31.103 + /// </returns>
31.104 + public OxyColor GetColor(double value)
31.105 + {
31.106 + return this.GetColor(this.GetPaletteIndex(value));
31.107 + }
31.108 +
31.109 + /// <summary>
31.110 + /// Gets the colors.
31.111 + /// </summary>
31.112 + /// <returns>The colors.</returns>
31.113 + public IEnumerable<OxyColor> GetColors()
31.114 + {
31.115 + yield return this.LowColor;
31.116 + foreach (var color in this.Palette.Colors)
31.117 + {
31.118 + yield return color;
31.119 + }
31.120 +
31.121 + yield return this.HighColor;
31.122 + }
31.123 +
31.124 + /// <summary>
31.125 + /// Gets the palette index of the specified value.
31.126 + /// </summary>
31.127 + /// <param name="value">
31.128 + /// The value.
31.129 + /// </param>
31.130 + /// <returns>
31.131 + /// The palette index.
31.132 + /// </returns>
31.133 + /// <remarks>
31.134 + /// If the value is less than minimum, 0 is returned. If the value is greater than maximum, Palette.Colors.Count+1 is returned.
31.135 + /// </remarks>
31.136 + public int GetPaletteIndex(double value)
31.137 + {
31.138 + if (this.LowColor != null && value < this.Minimum)
31.139 + {
31.140 + return 0;
31.141 + }
31.142 +
31.143 + if (this.HighColor != null && value > this.Maximum)
31.144 + {
31.145 + return this.Palette.Colors.Count + 1;
31.146 + }
31.147 +
31.148 + int index = 1 + (int)((value - this.ActualMinimum) / (this.ActualMaximum - this.ActualMinimum) * this.Palette.Colors.Count);
31.149 +
31.150 + if (index < 1)
31.151 + {
31.152 + index = 1;
31.153 + }
31.154 +
31.155 + if (index > this.Palette.Colors.Count)
31.156 + {
31.157 + index = this.Palette.Colors.Count;
31.158 + }
31.159 +
31.160 + return index;
31.161 + }
31.162 +
31.163 + /// <summary>
31.164 + /// Determines whether the axis is used for X/Y values.
31.165 + /// </summary>
31.166 + /// <returns>
31.167 + /// <c>true</c> if it is an XY axis; otherwise, <c>false</c> .
31.168 + /// </returns>
31.169 + public override bool IsXyAxis()
31.170 + {
31.171 + return false;
31.172 + }
31.173 +
31.174 + /// <summary>
31.175 + /// Renders the axis on the specified render context.
31.176 + /// </summary>
31.177 + /// <param name="rc">The render context.</param>
31.178 + /// <param name="model">The model.</param>
31.179 + /// <param name="axisLayer">The rendering order.</param>
31.180 + /// <param name="pass">The render pass.</param>
31.181 + public override void Render(IRenderContext rc, PlotModel model, AxisLayer axisLayer, int pass)
31.182 + {
31.183 + if (this.Position == AxisPosition.None)
31.184 + {
31.185 + return;
31.186 + }
31.187 +
31.188 + if (pass == 0)
31.189 + {
31.190 + double left = model.PlotArea.Left;
31.191 + double top = model.PlotArea.Top;
31.192 + double width = this.MajorTickSize - 2;
31.193 + double height = this.MajorTickSize - 2;
31.194 +
31.195 + switch (this.Position)
31.196 + {
31.197 + case AxisPosition.Left:
31.198 + left = model.PlotArea.Left - this.PositionTierMinShift - width;
31.199 + top = model.PlotArea.Top;
31.200 + break;
31.201 + case AxisPosition.Right:
31.202 + left = model.PlotArea.Right + this.PositionTierMinShift;
31.203 + top = model.PlotArea.Top;
31.204 + break;
31.205 + case AxisPosition.Top:
31.206 + left = model.PlotArea.Left;
31.207 + top = model.PlotArea.Top - this.PositionTierMinShift - height;
31.208 + break;
31.209 + case AxisPosition.Bottom:
31.210 + left = model.PlotArea.Left;
31.211 + top = model.PlotArea.Bottom + this.PositionTierMinShift;
31.212 + break;
31.213 + }
31.214 +
31.215 + Action<double, double, OxyColor> drawColorRect = (ylow, yhigh, color) =>
31.216 + {
31.217 + double ymin = Math.Min(ylow, yhigh);
31.218 + double ymax = Math.Max(ylow, yhigh);
31.219 + rc.DrawRectangle(
31.220 + this.IsHorizontal()
31.221 + ? new OxyRect(ymin, top, ymax - ymin, height)
31.222 + : new OxyRect(left, ymin, width, ymax - ymin),
31.223 + color,
31.224 + null);
31.225 + };
31.226 +
31.227 + int n = this.Palette.Colors.Count;
31.228 + for (int i = 0; i < n; i++)
31.229 + {
31.230 + double ylow = this.Transform(this.GetLowValue(i));
31.231 + double yhigh = this.Transform(this.GetHighValue(i));
31.232 + drawColorRect(ylow, yhigh, this.Palette.Colors[i]);
31.233 + }
31.234 +
31.235 + double highLowLength = 10;
31.236 + if (this.IsHorizontal())
31.237 + {
31.238 + highLowLength *= -1;
31.239 + }
31.240 +
31.241 + if (this.LowColor != null)
31.242 + {
31.243 + double ylow = this.Transform(this.ActualMinimum);
31.244 + drawColorRect(ylow, ylow + highLowLength, this.LowColor);
31.245 + }
31.246 +
31.247 + if (this.HighColor != null)
31.248 + {
31.249 + double yhigh = this.Transform(this.ActualMaximum);
31.250 + drawColorRect(yhigh, yhigh - highLowLength, this.HighColor);
31.251 + }
31.252 + }
31.253 +
31.254 + base.Render(rc, model, axisLayer, pass);
31.255 + }
31.256 +
31.257 + /// <summary>
31.258 + /// Gets the high value of the specified palette index.
31.259 + /// </summary>
31.260 + /// <param name="paletteIndex">
31.261 + /// Index of the palette.
31.262 + /// </param>
31.263 + /// <returns>
31.264 + /// The value.
31.265 + /// </returns>
31.266 + protected double GetHighValue(int paletteIndex)
31.267 + {
31.268 + return this.GetLowValue(paletteIndex + 1);
31.269 + }
31.270 +
31.271 + /// <summary>
31.272 + /// Gets the low value of the specified palette index.
31.273 + /// </summary>
31.274 + /// <param name="paletteIndex">
31.275 + /// Index of the palette.
31.276 + /// </param>
31.277 + /// <returns>
31.278 + /// The value.
31.279 + /// </returns>
31.280 + protected double GetLowValue(int paletteIndex)
31.281 + {
31.282 + return ((double)paletteIndex / this.Palette.Colors.Count * (this.ActualMaximum - this.ActualMinimum))
31.283 + + this.ActualMinimum;
31.284 + }
31.285 + }
31.286 +}
31.287 \ No newline at end of file
32.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
32.2 +++ b/External/OxyPlot/OxyPlot/Axes/DateTimeAxis.cs Sat Jun 08 16:53:22 2013 +0000
32.3 @@ -0,0 +1,679 @@
32.4 +// --------------------------------------------------------------------------------------------------------------------
32.5 +// <copyright file="DateTimeAxis.cs" company="OxyPlot">
32.6 +// The MIT License (MIT)
32.7 +//
32.8 +// Copyright (c) 2012 Oystein Bjorke
32.9 +//
32.10 +// Permission is hereby granted, free of charge, to any person obtaining a
32.11 +// copy of this software and associated documentation files (the
32.12 +// "Software"), to deal in the Software without restriction, including
32.13 +// without limitation the rights to use, copy, modify, merge, publish,
32.14 +// distribute, sublicense, and/or sell copies of the Software, and to
32.15 +// permit persons to whom the Software is furnished to do so, subject to
32.16 +// the following conditions:
32.17 +//
32.18 +// The above copyright notice and this permission notice shall be included
32.19 +// in all copies or substantial portions of the Software.
32.20 +//
32.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
32.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
32.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
32.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
32.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
32.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
32.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
32.28 +// </copyright>
32.29 +// <summary>
32.30 +// Represents a DateTime axis.
32.31 +// </summary>
32.32 +// --------------------------------------------------------------------------------------------------------------------
32.33 +
32.34 +namespace OxyPlot.Axes
32.35 +{
32.36 + using System;
32.37 + using System.Collections.Generic;
32.38 + using System.Collections.ObjectModel;
32.39 + using System.Globalization;
32.40 + using System.Linq;
32.41 +
32.42 + /// <summary>
32.43 + /// Represents a axis presenting <see cref="System.DateTime"/> values.
32.44 + /// </summary>
32.45 + /// <remarks>
32.46 + /// The actual numeric values on the axis are days since 1900/01/01.
32.47 + /// Use the static ToDouble and ToDateTime to convert numeric values to DateTimes.
32.48 + /// The StringFormat value can be used to force formatting of the axis values
32.49 + /// "yyyy-MM-dd" shows date
32.50 + /// "w" or "ww" shows week number
32.51 + /// "h:mm" shows hours and minutes
32.52 + /// </remarks>
32.53 + public class DateTimeAxis : LinearAxis
32.54 + {
32.55 + /// <summary>
32.56 + /// The time origin.
32.57 + /// </summary>
32.58 + /// <remarks>
32.59 + /// Same date values as Excel
32.60 + /// </remarks>
32.61 + private static DateTime timeOrigin = new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc);
32.62 +
32.63 + /// <summary>
32.64 + /// The actual interval type.
32.65 + /// </summary>
32.66 + private DateTimeIntervalType actualIntervalType;
32.67 +
32.68 + /// <summary>
32.69 + /// The actual minor interval type.
32.70 + /// </summary>
32.71 + private DateTimeIntervalType actualMinorIntervalType;
32.72 +
32.73 + /// <summary>
32.74 + /// Initializes a new instance of the <see cref = "DateTimeAxis" /> class.
32.75 + /// </summary>
32.76 + public DateTimeAxis()
32.77 + {
32.78 + this.Position = AxisPosition.Bottom;
32.79 + this.IntervalType = DateTimeIntervalType.Auto;
32.80 + this.FirstDayOfWeek = DayOfWeek.Monday;
32.81 + this.CalendarWeekRule = CalendarWeekRule.FirstFourDayWeek;
32.82 + }
32.83 +
32.84 + /// <summary>
32.85 + /// Initializes a new instance of the <see cref="DateTimeAxis"/> class.
32.86 + /// </summary>
32.87 + /// <param name="pos">
32.88 + /// The position.
32.89 + /// </param>
32.90 + /// <param name="title">
32.91 + /// The axis title.
32.92 + /// </param>
32.93 + /// <param name="format">
32.94 + /// The string format for the axis values.
32.95 + /// </param>
32.96 + /// <param name="intervalType">
32.97 + /// The interval type.
32.98 + /// </param>
32.99 + public DateTimeAxis(
32.100 + AxisPosition pos = AxisPosition.Bottom,
32.101 + string title = null,
32.102 + string format = null,
32.103 + DateTimeIntervalType intervalType = DateTimeIntervalType.Auto)
32.104 + : base(pos, title)
32.105 + {
32.106 + this.FirstDayOfWeek = DayOfWeek.Monday;
32.107 + this.CalendarWeekRule = CalendarWeekRule.FirstFourDayWeek;
32.108 +
32.109 + this.StringFormat = format;
32.110 + this.IntervalType = intervalType;
32.111 + }
32.112 +
32.113 + /// <summary>
32.114 + /// Initializes a new instance of the <see cref="DateTimeAxis"/> class.
32.115 + /// </summary>
32.116 + /// <param name="firstDateTime">
32.117 + /// The first date/time on the axis.
32.118 + /// </param>
32.119 + /// <param name="lastDateTime">
32.120 + /// The last date/time on the axis.
32.121 + /// </param>
32.122 + /// <param name="pos">
32.123 + /// The position of the axis.
32.124 + /// </param>
32.125 + /// <param name="title">
32.126 + /// The axis title.
32.127 + /// </param>
32.128 + /// <param name="format">
32.129 + /// The string format for the axis values.
32.130 + /// </param>
32.131 + /// <param name="intervalType">
32.132 + /// The interval type.
32.133 + /// </param>
32.134 + [Obsolete]
32.135 + public DateTimeAxis(
32.136 + DateTime firstDateTime,
32.137 + DateTime lastDateTime,
32.138 + AxisPosition pos = AxisPosition.Bottom,
32.139 + string title = null,
32.140 + string format = null,
32.141 + DateTimeIntervalType intervalType = DateTimeIntervalType.Auto)
32.142 + : this(pos, title, format, intervalType)
32.143 + {
32.144 + this.Minimum = ToDouble(firstDateTime);
32.145 + this.Maximum = ToDouble(lastDateTime);
32.146 + }
32.147 +
32.148 + /// <summary>
32.149 + /// Initializes a new instance of the <see cref="DateTimeAxis" /> class.
32.150 + /// </summary>
32.151 + /// <param name="pos">The position of the axis.</param>
32.152 + /// <param name="firstDateTime">The first date/time on the axis.</param>
32.153 + /// <param name="lastDateTime">The last date/time on the axis.</param>
32.154 + /// <param name="title">The axis title.</param>
32.155 + /// <param name="format">The string format for the axis values.</param>
32.156 + /// <param name="intervalType">The interval type.</param>
32.157 + public DateTimeAxis(
32.158 + AxisPosition pos,
32.159 + DateTime firstDateTime,
32.160 + DateTime lastDateTime,
32.161 + string title = null,
32.162 + string format = null,
32.163 + DateTimeIntervalType intervalType = DateTimeIntervalType.Auto)
32.164 + : this(pos, title, format, intervalType)
32.165 + {
32.166 + this.Minimum = ToDouble(firstDateTime);
32.167 + this.Maximum = ToDouble(lastDateTime);
32.168 + }
32.169 +
32.170 + /// <summary>
32.171 + /// Gets or sets CalendarWeekRule.
32.172 + /// </summary>
32.173 + public CalendarWeekRule CalendarWeekRule { get; set; }
32.174 +
32.175 + /// <summary>
32.176 + /// Gets or sets FirstDayOfWeek.
32.177 + /// </summary>
32.178 + public DayOfWeek FirstDayOfWeek { get; set; }
32.179 +
32.180 + /// <summary>
32.181 + /// Gets or sets IntervalType.
32.182 + /// </summary>
32.183 + public DateTimeIntervalType IntervalType { get; set; }
32.184 +
32.185 + /// <summary>
32.186 + /// Gets or sets MinorIntervalType.
32.187 + /// </summary>
32.188 + public DateTimeIntervalType MinorIntervalType { get; set; }
32.189 +
32.190 + /// <summary>
32.191 + /// Gets or sets the time zone (used when formatting date/time values).
32.192 + /// </summary>
32.193 + /// <remarks>
32.194 + /// No date/time conversion will be performed if this property is null.
32.195 + /// </remarks>
32.196 + /// <value>
32.197 + /// The time zone info.
32.198 + /// </value>
32.199 + public TimeZoneInfo TimeZone { get; set; }
32.200 +
32.201 + /// <summary>
32.202 + /// Creates a data point.
32.203 + /// </summary>
32.204 + /// <param name="x">
32.205 + /// The x value.
32.206 + /// </param>
32.207 + /// <param name="y">
32.208 + /// The y value.
32.209 + /// </param>
32.210 + /// <returns>
32.211 + /// A data point.
32.212 + /// </returns>
32.213 + public static DataPoint CreateDataPoint(DateTime x, double y)
32.214 + {
32.215 + return new DataPoint(ToDouble(x), y);
32.216 + }
32.217 +
32.218 + /// <summary>
32.219 + /// Creates a data point.
32.220 + /// </summary>
32.221 + /// <param name="x">
32.222 + /// The x value.
32.223 + /// </param>
32.224 + /// <param name="y">
32.225 + /// The y value.
32.226 + /// </param>
32.227 + /// <returns>
32.228 + /// A data point.
32.229 + /// </returns>
32.230 + public static DataPoint CreateDataPoint(DateTime x, DateTime y)
32.231 + {
32.232 + return new DataPoint(ToDouble(x), ToDouble(y));
32.233 + }
32.234 +
32.235 + /// <summary>
32.236 + /// Creates a data point.
32.237 + /// </summary>
32.238 + /// <param name="x">
32.239 + /// The x value.
32.240 + /// </param>
32.241 + /// <param name="y">
32.242 + /// The y value.
32.243 + /// </param>
32.244 + /// <returns>
32.245 + /// A data point.
32.246 + /// </returns>
32.247 + public static DataPoint CreateDataPoint(double x, DateTime y)
32.248 + {
32.249 + return new DataPoint(x, ToDouble(y));
32.250 + }
32.251 +
32.252 + /// <summary>
32.253 + /// Converts a numeric representation of the date (number of days after the time origin) to a DateTime structure.
32.254 + /// </summary>
32.255 + /// <param name="value">
32.256 + /// The number of days after the time origin.
32.257 + /// </param>
32.258 + /// <returns>
32.259 + /// A date/time structure.
32.260 + /// </returns>
32.261 + public static DateTime ToDateTime(double value)
32.262 + {
32.263 + if (double.IsNaN(value))
32.264 + {
32.265 + return new DateTime();
32.266 + }
32.267 +
32.268 + return timeOrigin.AddDays(value - 1);
32.269 + }
32.270 +
32.271 + /// <summary>
32.272 + /// Converts a DateTime to days after the time origin.
32.273 + /// </summary>
32.274 + /// <param name="value">
32.275 + /// The date/time structure.
32.276 + /// </param>
32.277 + /// <returns>
32.278 + /// The number of days after the time origin.
32.279 + /// </returns>
32.280 + public static double ToDouble(DateTime value)
32.281 + {
32.282 + var span = value - timeOrigin;
32.283 + return span.TotalDays + 1;
32.284 + }
32.285 +
32.286 + /// <summary>
32.287 + /// Formats the specified value by the axis' ActualStringFormat.
32.288 + /// </summary>
32.289 + /// <param name="x">
32.290 + /// The x.
32.291 + /// </param>
32.292 + /// <returns>
32.293 + /// The formatted DateTime value
32.294 + /// </returns>
32.295 + public override string FormatValue(double x)
32.296 + {
32.297 + // convert the double value to a DateTime
32.298 + var time = ToDateTime(x);
32.299 +
32.300 + // If a time zone is specified, convert the time
32.301 + if (this.TimeZone != null)
32.302 + {
32.303 + time = TimeZoneInfo.ConvertTime(time, this.TimeZone);
32.304 + }
32.305 +
32.306 + string fmt = this.ActualStringFormat;
32.307 + if (fmt == null)
32.308 + {
32.309 + return time.ToString(CultureInfo.CurrentCulture.DateTimeFormat.ShortDatePattern);
32.310 + }
32.311 +
32.312 + int week = this.GetWeek(time);
32.313 + fmt = fmt.Replace("ww", week.ToString("00"));
32.314 + fmt = fmt.Replace("w", week.ToString(CultureInfo.InvariantCulture));
32.315 + return time.ToString(fmt, this.ActualCulture);
32.316 + }
32.317 +
32.318 + /// <summary>
32.319 + /// Gets the tick values.
32.320 + /// </summary>
32.321 + /// <param name="majorLabelValues">
32.322 + /// The major label values.
32.323 + /// </param>
32.324 + /// <param name="majorTickValues">
32.325 + /// The major tick values.
32.326 + /// </param>
32.327 + /// <param name="minorTickValues">
32.328 + /// The minor tick values.
32.329 + /// </param>
32.330 + public override void GetTickValues(
32.331 + out IList<double> majorLabelValues, out IList<double> majorTickValues, out IList<double> minorTickValues)
32.332 + {
32.333 + minorTickValues = this.CreateDateTimeTickValues(
32.334 + this.ActualMinimum, this.ActualMaximum, this.ActualMinorStep, this.actualMinorIntervalType);
32.335 + majorTickValues = this.CreateDateTimeTickValues(
32.336 + this.ActualMinimum, this.ActualMaximum, this.ActualMajorStep, this.actualIntervalType);
32.337 + majorLabelValues = majorTickValues;
32.338 + }
32.339 +
32.340 + /// <summary>
32.341 + /// Gets the value from an axis coordinate, converts from double to the correct data type if necessary.
32.342 + /// e.g. DateTimeAxis returns the DateTime and CategoryAxis returns category strings.
32.343 + /// </summary>
32.344 + /// <param name="x">
32.345 + /// The coordinate.
32.346 + /// </param>
32.347 + /// <returns>
32.348 + /// The value.
32.349 + /// </returns>
32.350 + public override object GetValue(double x)
32.351 + {
32.352 + var time = ToDateTime(x);
32.353 +
32.354 + if (this.TimeZone != null)
32.355 + {
32.356 + time = TimeZoneInfo.ConvertTime(time, this.TimeZone);
32.357 + }
32.358 +
32.359 + return time;
32.360 + }
32.361 +
32.362 + /// <summary>
32.363 + /// Updates the intervals.
32.364 + /// </summary>
32.365 + /// <param name="plotArea">
32.366 + /// The plot area.
32.367 + /// </param>
32.368 + internal override void UpdateIntervals(OxyRect plotArea)
32.369 + {
32.370 + base.UpdateIntervals(plotArea);
32.371 + switch (this.actualIntervalType)
32.372 + {
32.373 + case DateTimeIntervalType.Years:
32.374 + this.ActualMinorStep = 31;
32.375 + this.actualMinorIntervalType = DateTimeIntervalType.Years;
32.376 + if (this.ActualStringFormat == null)
32.377 + {
32.378 + this.ActualStringFormat = "yyyy";
32.379 + }
32.380 +
32.381 + break;
32.382 + case DateTimeIntervalType.Months:
32.383 + this.actualMinorIntervalType = DateTimeIntervalType.Months;
32.384 + if (this.ActualStringFormat == null)
32.385 + {
32.386 + this.ActualStringFormat = "yyyy-MM-dd";
32.387 + }
32.388 +
32.389 + break;
32.390 + case DateTimeIntervalType.Weeks:
32.391 + this.actualMinorIntervalType = DateTimeIntervalType.Days;
32.392 + this.ActualMajorStep = 7;
32.393 + this.ActualMinorStep = 1;
32.394 + if (this.ActualStringFormat == null)
32.395 + {
32.396 + this.ActualStringFormat = "yyyy/ww";
32.397 + }
32.398 +
32.399 + break;
32.400 + case DateTimeIntervalType.Days:
32.401 + this.ActualMinorStep = this.ActualMajorStep;
32.402 + if (this.ActualStringFormat == null)
32.403 + {
32.404 + this.ActualStringFormat = "yyyy-MM-dd";
32.405 + }
32.406 +
32.407 + break;
32.408 + case DateTimeIntervalType.Hours:
32.409 + this.ActualMinorStep = this.ActualMajorStep;
32.410 + if (this.ActualStringFormat == null)
32.411 + {
32.412 + this.ActualStringFormat = "HH:mm";
32.413 + }
32.414 +
32.415 + break;
32.416 + case DateTimeIntervalType.Minutes:
32.417 + this.ActualMinorStep = this.ActualMajorStep;
32.418 + if (this.ActualStringFormat == null)
32.419 + {
32.420 + this.ActualStringFormat = "HH:mm";
32.421 + }
32.422 +
32.423 + break;
32.424 + case DateTimeIntervalType.Seconds:
32.425 + this.ActualMinorStep = this.ActualMajorStep;
32.426 + if (this.ActualStringFormat == null)
32.427 + {
32.428 + this.ActualStringFormat = "HH:mm:ss";
32.429 + }
32.430 +
32.431 + break;
32.432 + case DateTimeIntervalType.Manual:
32.433 + break;
32.434 + case DateTimeIntervalType.Auto:
32.435 + break;
32.436 + }
32.437 + }
32.438 +
32.439 + /// <summary>
32.440 + /// Calculates the actual interval.
32.441 + /// </summary>
32.442 + /// <param name="availableSize">
32.443 + /// Size of the available area.
32.444 + /// </param>
32.445 + /// <param name="maxIntervalSize">
32.446 + /// Maximum length of the intervals.
32.447 + /// </param>
32.448 + /// <returns>
32.449 + /// The calculate actual interval.
32.450 + /// </returns>
32.451 + protected override double CalculateActualInterval(double availableSize, double maxIntervalSize)
32.452 + {
32.453 + const double Year = 365.25;
32.454 + const double Month = 30.5;
32.455 + const double Week = 7;
32.456 + const double Day = 1.0;
32.457 + const double Hour = Day / 24;
32.458 + const double Minute = Hour / 60;
32.459 + const double Second = Minute / 60;
32.460 +
32.461 + double range = Math.Abs(this.ActualMinimum - this.ActualMaximum);
32.462 +
32.463 + var goodIntervals = new[]
32.464 + {
32.465 + Second, 2 * Second, 5 * Second, 10 * Second, 30 * Second, Minute, 2 * Minute,
32.466 + 5 * Minute, 10 * Minute, 30 * Minute, Hour, 4 * Hour, 8 * Hour, 12 * Hour, Day,
32.467 + 2 * Day, 5 * Day, Week, 2 * Week, Month, 2 * Month, 3 * Month, 4 * Month,
32.468 + 6 * Month, Year
32.469 + };
32.470 +
32.471 + double interval = goodIntervals[0];
32.472 +
32.473 + int maxNumberOfIntervals = Math.Max((int)(availableSize / maxIntervalSize), 2);
32.474 +
32.475 + while (true)
32.476 + {
32.477 + if (range / interval < maxNumberOfIntervals)
32.478 + {
32.479 + break;
32.480 + }
32.481 +
32.482 + double nextInterval = goodIntervals.FirstOrDefault(i => i > interval);
32.483 + if (Math.Abs(nextInterval) < double.Epsilon)
32.484 + {
32.485 + nextInterval = interval * 2;
32.486 + }
32.487 +
32.488 + interval = nextInterval;
32.489 + }
32.490 +
32.491 + this.actualIntervalType = this.IntervalType;
32.492 + this.actualMinorIntervalType = this.MinorIntervalType;
32.493 +
32.494 + if (this.IntervalType == DateTimeIntervalType.Auto)
32.495 + {
32.496 + this.actualIntervalType = DateTimeIntervalType.Seconds;
32.497 + if (interval >= 1.0 / 24 / 60)
32.498 + {
32.499 + this.actualIntervalType = DateTimeIntervalType.Minutes;
32.500 + }
32.501 +
32.502 + if (interval >= 1.0 / 24)
32.503 + {
32.504 + this.actualIntervalType = DateTimeIntervalType.Hours;
32.505 + }
32.506 +
32.507 + if (interval >= 1)
32.508 + {
32.509 + this.actualIntervalType = DateTimeIntervalType.Days;
32.510 + }
32.511 +
32.512 + if (interval >= 30)
32.513 + {
32.514 + this.actualIntervalType = DateTimeIntervalType.Months;
32.515 + }
32.516 +
32.517 + if (range >= 365.25)
32.518 + {
32.519 + this.actualIntervalType = DateTimeIntervalType.Years;
32.520 + }
32.521 + }
32.522 +
32.523 + if (this.actualIntervalType == DateTimeIntervalType.Months)
32.524 + {
32.525 + double monthsRange = range / 30.5;
32.526 + interval = this.CalculateActualInterval(availableSize, maxIntervalSize, monthsRange);
32.527 + }
32.528 +
32.529 + if (this.actualIntervalType == DateTimeIntervalType.Years)
32.530 + {
32.531 + double yearsRange = range / 365.25;
32.532 + interval = this.CalculateActualInterval(availableSize, maxIntervalSize, yearsRange);
32.533 + }
32.534 +
32.535 + if (this.actualMinorIntervalType == DateTimeIntervalType.Auto)
32.536 + {
32.537 + switch (this.actualIntervalType)
32.538 + {
32.539 + case DateTimeIntervalType.Years:
32.540 + this.actualMinorIntervalType = DateTimeIntervalType.Months;
32.541 + break;
32.542 + case DateTimeIntervalType.Months:
32.543 + this.actualMinorIntervalType = DateTimeIntervalType.Days;
32.544 + break;
32.545 + case DateTimeIntervalType.Weeks:
32.546 + this.actualMinorIntervalType = DateTimeIntervalType.Days;
32.547 + break;
32.548 + case DateTimeIntervalType.Days:
32.549 + this.actualMinorIntervalType = DateTimeIntervalType.Hours;
32.550 + break;
32.551 + case DateTimeIntervalType.Hours:
32.552 + this.actualMinorIntervalType = DateTimeIntervalType.Minutes;
32.553 + break;
32.554 + default:
32.555 + this.actualMinorIntervalType = DateTimeIntervalType.Days;
32.556 + break;
32.557 + }
32.558 + }
32.559 +
32.560 + return interval;
32.561 + }
32.562 +
32.563 + /// <summary>
32.564 + /// Creates the date tick values.
32.565 + /// </summary>
32.566 + /// <param name="min">
32.567 + /// The min.
32.568 + /// </param>
32.569 + /// <param name="max">
32.570 + /// The max.
32.571 + /// </param>
32.572 + /// <param name="step">
32.573 + /// The step.
32.574 + /// </param>
32.575 + /// <param name="intervalType">
32.576 + /// Type of the interval.
32.577 + /// </param>
32.578 + /// <returns>
32.579 + /// Date tick values.
32.580 + /// </returns>
32.581 + private IList<double> CreateDateTickValues(
32.582 + double min, double max, double step, DateTimeIntervalType intervalType)
32.583 + {
32.584 + DateTime start = ToDateTime(min);
32.585 + switch (intervalType)
32.586 + {
32.587 + case DateTimeIntervalType.Weeks:
32.588 +
32.589 + // make sure the first tick is at the 1st day of a week
32.590 + start = start.AddDays(-(int)start.DayOfWeek + (int)this.FirstDayOfWeek);
32.591 + break;
32.592 + case DateTimeIntervalType.Months:
32.593 +
32.594 + // make sure the first tick is at the 1st of a month
32.595 + start = new DateTime(start.Year, start.Month, 1);
32.596 + break;
32.597 + case DateTimeIntervalType.Years:
32.598 +
32.599 + // make sure the first tick is at Jan 1st
32.600 + start = new DateTime(start.Year, 1, 1);
32.601 + break;
32.602 + }
32.603 +
32.604 + // Adds a tick to the end time to make sure the end DateTime is included.
32.605 + DateTime end = ToDateTime(max).AddTicks(1);
32.606 +
32.607 + DateTime current = start;
32.608 + var values = new Collection<double>();
32.609 + double eps = step * 1e-3;
32.610 + DateTime minDateTime = ToDateTime(min - eps);
32.611 + DateTime maxDateTime = ToDateTime(max + eps);
32.612 + while (current < end)
32.613 + {
32.614 + if (current > minDateTime && current < maxDateTime)
32.615 + {
32.616 + values.Add(ToDouble(current));
32.617 + }
32.618 +
32.619 + switch (intervalType)
32.620 + {
32.621 + case DateTimeIntervalType.Months:
32.622 + current = current.AddMonths((int)Math.Ceiling(step));
32.623 + break;
32.624 + case DateTimeIntervalType.Years:
32.625 + current = current.AddYears((int)Math.Ceiling(step));
32.626 + break;
32.627 + default:
32.628 + current = current.AddDays(step);
32.629 + break;
32.630 + }
32.631 + }
32.632 +
32.633 + return values;
32.634 + }
32.635 +
32.636 + /// <summary>
32.637 + /// Creates date/time tick values.
32.638 + /// </summary>
32.639 + /// <param name="min">
32.640 + /// The min.
32.641 + /// </param>
32.642 + /// <param name="max">
32.643 + /// The max.
32.644 + /// </param>
32.645 + /// <param name="interval">
32.646 + /// The interval.
32.647 + /// </param>
32.648 + /// <param name="intervalType">
32.649 + /// The interval type.
32.650 + /// </param>
32.651 + /// DateTime tick values.
32.652 + /// <returns>
32.653 + /// DateTime tick values.
32.654 + /// </returns>
32.655 + private IList<double> CreateDateTimeTickValues(
32.656 + double min, double max, double interval, DateTimeIntervalType intervalType)
32.657 + {
32.658 + // If the step size is more than 7 days (e.g. months or years) we use a specialized tick generation method that adds tick values with uneven spacing...
32.659 + if (intervalType > DateTimeIntervalType.Days)
32.660 + {
32.661 + return this.CreateDateTickValues(min, max, interval, intervalType);
32.662 + }
32.663 +
32.664 + // For shorter step sizes we use the method from Axis
32.665 + return CreateTickValues(min, max, interval);
32.666 + }
32.667 +
32.668 + /// <summary>
32.669 + /// Gets the week number for the specified date.
32.670 + /// </summary>
32.671 + /// <param name="date">
32.672 + /// The date.
32.673 + /// </param>
32.674 + /// <returns>
32.675 + /// The week number for the current culture.
32.676 + /// </returns>
32.677 + private int GetWeek(DateTime date)
32.678 + {
32.679 + return this.ActualCulture.Calendar.GetWeekOfYear(date, this.CalendarWeekRule, this.FirstDayOfWeek);
32.680 + }
32.681 + }
32.682 +}
32.683 \ No newline at end of file
33.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
33.2 +++ b/External/OxyPlot/OxyPlot/Axes/DateTimeIntervalType.cs Sat Jun 08 16:53:22 2013 +0000
33.3 @@ -0,0 +1,87 @@
33.4 +// --------------------------------------------------------------------------------------------------------------------
33.5 +// <copyright file="DateTimeIntervalType.cs" company="OxyPlot">
33.6 +// The MIT License (MIT)
33.7 +//
33.8 +// Copyright (c) 2012 Oystein Bjorke
33.9 +//
33.10 +// Permission is hereby granted, free of charge, to any person obtaining a
33.11 +// copy of this software and associated documentation files (the
33.12 +// "Software"), to deal in the Software without restriction, including
33.13 +// without limitation the rights to use, copy, modify, merge, publish,
33.14 +// distribute, sublicense, and/or sell copies of the Software, and to
33.15 +// permit persons to whom the Software is furnished to do so, subject to
33.16 +// the following conditions:
33.17 +//
33.18 +// The above copyright notice and this permission notice shall be included
33.19 +// in all copies or substantial portions of the Software.
33.20 +//
33.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
33.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
33.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
33.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
33.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
33.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
33.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
33.28 +// </copyright>
33.29 +// <summary>
33.30 +// Defines the date time interval for DateTimeAxis.
33.31 +// </summary>
33.32 +// --------------------------------------------------------------------------------------------------------------------
33.33 +namespace OxyPlot.Axes
33.34 +{
33.35 + /// <summary>
33.36 + /// Specifies the date time interval for <see cref="DateTimeAxis"/>.
33.37 + /// </summary>
33.38 + public enum DateTimeIntervalType
33.39 + {
33.40 + /// <summary>
33.41 + /// Automatically determine interval.
33.42 + /// </summary>
33.43 + Auto = 0,
33.44 +
33.45 + /// <summary>
33.46 + /// Manual definition of intervals.
33.47 + /// </summary>
33.48 + Manual = 1,
33.49 +
33.50 + /// <summary>
33.51 + /// Interval type is milliseconds.
33.52 + /// </summary>
33.53 + Milliseconds = 2,
33.54 +
33.55 + /// <summary>
33.56 + /// Interval type is seconds.
33.57 + /// </summary>
33.58 + Seconds = 3,
33.59 +
33.60 + /// <summary>
33.61 + /// Interval type is minutes.
33.62 + /// </summary>
33.63 + Minutes = 4,
33.64 +
33.65 + /// <summary>
33.66 + /// Interval type is hours.
33.67 + /// </summary>
33.68 + Hours = 5,
33.69 +
33.70 + /// <summary>
33.71 + /// Interval type is days.
33.72 + /// </summary>
33.73 + Days = 6,
33.74 +
33.75 + /// <summary>
33.76 + /// Interval type is weeks.
33.77 + /// </summary>
33.78 + Weeks = 7,
33.79 +
33.80 + /// <summary>
33.81 + /// Interval type is months.
33.82 + /// </summary>
33.83 + Months = 8,
33.84 +
33.85 + /// <summary>
33.86 + /// Interval type is years.
33.87 + /// </summary>
33.88 + Years = 9,
33.89 + }
33.90 +}
33.91 \ No newline at end of file
34.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
34.2 +++ b/External/OxyPlot/OxyPlot/Axes/LinearAxis.cs Sat Jun 08 16:53:22 2013 +0000
34.3 @@ -0,0 +1,164 @@
34.4 +// --------------------------------------------------------------------------------------------------------------------
34.5 +// <copyright file="LinearAxis.cs" company="OxyPlot">
34.6 +// The MIT License (MIT)
34.7 +//
34.8 +// Copyright (c) 2012 Oystein Bjorke
34.9 +//
34.10 +// Permission is hereby granted, free of charge, to any person obtaining a
34.11 +// copy of this software and associated documentation files (the
34.12 +// "Software"), to deal in the Software without restriction, including
34.13 +// without limitation the rights to use, copy, modify, merge, publish,
34.14 +// distribute, sublicense, and/or sell copies of the Software, and to
34.15 +// permit persons to whom the Software is furnished to do so, subject to
34.16 +// the following conditions:
34.17 +//
34.18 +// The above copyright notice and this permission notice shall be included
34.19 +// in all copies or substantial portions of the Software.
34.20 +//
34.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
34.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
34.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
34.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
34.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
34.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
34.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
34.28 +// </copyright>
34.29 +// <summary>
34.30 +// Represents an axis with linear scale.
34.31 +// </summary>
34.32 +// --------------------------------------------------------------------------------------------------------------------
34.33 +namespace OxyPlot.Axes
34.34 +{
34.35 + /// <summary>
34.36 + /// Represents an axis with linear scale.
34.37 + /// </summary>
34.38 + public class LinearAxis : Axis
34.39 + {
34.40 + /// <summary>
34.41 + /// Initializes a new instance of the <see cref="LinearAxis"/> class.
34.42 + /// </summary>
34.43 + public LinearAxis()
34.44 + {
34.45 + this.FractionUnit = 1.0;
34.46 + this.FractionUnitSymbol = null;
34.47 + this.FormatAsFractions = false;
34.48 + }
34.49 +
34.50 + /// <summary>
34.51 + /// Initializes a new instance of the <see cref="LinearAxis"/> class.
34.52 + /// </summary>
34.53 + /// <param name="pos">
34.54 + /// The pos.
34.55 + /// </param>
34.56 + /// <param name="title">
34.57 + /// The title.
34.58 + /// </param>
34.59 + public LinearAxis(AxisPosition pos, string title)
34.60 + : this()
34.61 + {
34.62 + this.Position = pos;
34.63 + this.Title = title;
34.64 + }
34.65 +
34.66 + /// <summary>
34.67 + /// Initializes a new instance of the <see cref="LinearAxis"/> class.
34.68 + /// </summary>
34.69 + /// <param name="pos">
34.70 + /// The pos.
34.71 + /// </param>
34.72 + /// <param name="minimum">
34.73 + /// The minimum.
34.74 + /// </param>
34.75 + /// <param name="maximum">
34.76 + /// The maximum.
34.77 + /// </param>
34.78 + /// <param name="title">
34.79 + /// The title.
34.80 + /// </param>
34.81 + public LinearAxis(
34.82 + AxisPosition pos, double minimum = double.NaN, double maximum = double.NaN, string title = null)
34.83 + : this(pos, minimum, maximum, double.NaN, double.NaN, title)
34.84 + {
34.85 + }
34.86 +
34.87 + /// <summary>
34.88 + /// Initializes a new instance of the <see cref="LinearAxis"/> class.
34.89 + /// </summary>
34.90 + /// <param name="pos">
34.91 + /// The pos.
34.92 + /// </param>
34.93 + /// <param name="minimum">
34.94 + /// The minimum.
34.95 + /// </param>
34.96 + /// <param name="maximum">
34.97 + /// The maximum.
34.98 + /// </param>
34.99 + /// <param name="majorStep">
34.100 + /// The major step.
34.101 + /// </param>
34.102 + /// <param name="minorStep">
34.103 + /// The minor step.
34.104 + /// </param>
34.105 + /// <param name="title">
34.106 + /// The title.
34.107 + /// </param>
34.108 + public LinearAxis(
34.109 + AxisPosition pos, double minimum, double maximum, double majorStep, double minorStep, string title = null)
34.110 + : this(pos, title)
34.111 + {
34.112 + this.Minimum = minimum;
34.113 + this.Maximum = maximum;
34.114 + this.MajorStep = majorStep;
34.115 + this.MinorStep = minorStep;
34.116 + }
34.117 +
34.118 + /// <summary>
34.119 + /// Gets or sets a value indicating whether to format numbers as fractions.
34.120 + /// </summary>
34.121 + public bool FormatAsFractions { get; set; }
34.122 +
34.123 + /// <summary>
34.124 + /// Gets or sets the fraction unit. Remember to set FormatAsFractions to true.
34.125 + /// </summary>
34.126 + /// <value> The fraction unit. </value>
34.127 + public double FractionUnit { get; set; }
34.128 +
34.129 + /// <summary>
34.130 + /// Gets or sets the fraction unit symbol. Use FractionUnit = Math.PI and FractionUnitSymbol = "π" if you want the axis to show "π/2,π,3π/2,2π" etc. Use FractionUnit = 1 and FractionUnitSymbol = "L" if you want the axis to show "0,L/2,L" etc. Remember to set FormatAsFractions to true.
34.131 + /// </summary>
34.132 + /// <value> The fraction unit symbol. </value>
34.133 + public string FractionUnitSymbol { get; set; }
34.134 +
34.135 + /// <summary>
34.136 + /// Formats the value to be used on the axis.
34.137 + /// </summary>
34.138 + /// <param name="x">
34.139 + /// The value.
34.140 + /// </param>
34.141 + /// <returns>
34.142 + /// The formatted value.
34.143 + /// </returns>
34.144 + public override string FormatValue(double x)
34.145 + {
34.146 + if (this.FormatAsFractions)
34.147 + {
34.148 + return FractionHelper.ConvertToFractionString(
34.149 + x, this.FractionUnit, this.FractionUnitSymbol, 1e-6, this.ActualCulture);
34.150 + }
34.151 +
34.152 + return base.FormatValue(x);
34.153 + }
34.154 +
34.155 + /// <summary>
34.156 + /// Determines whether the axis is used for X/Y values.
34.157 + /// </summary>
34.158 + /// <returns>
34.159 + /// <c>true</c> if it is an XY axis; otherwise, <c>false</c> .
34.160 + /// </returns>
34.161 + public override bool IsXyAxis()
34.162 + {
34.163 + return true;
34.164 + }
34.165 +
34.166 + }
34.167 +}
34.168 \ No newline at end of file
35.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
35.2 +++ b/External/OxyPlot/OxyPlot/Axes/LogarithmicAxis.cs Sat Jun 08 16:53:22 2013 +0000
35.3 @@ -0,0 +1,406 @@
35.4 +// --------------------------------------------------------------------------------------------------------------------
35.5 +// <copyright file="LogarithmicAxis.cs" company="OxyPlot">
35.6 +// The MIT License (MIT)
35.7 +//
35.8 +// Copyright (c) 2012 Oystein Bjorke
35.9 +//
35.10 +// Permission is hereby granted, free of charge, to any person obtaining a
35.11 +// copy of this software and associated documentation files (the
35.12 +// "Software"), to deal in the Software without restriction, including
35.13 +// without limitation the rights to use, copy, modify, merge, publish,
35.14 +// distribute, sublicense, and/or sell copies of the Software, and to
35.15 +// permit persons to whom the Software is furnished to do so, subject to
35.16 +// the following conditions:
35.17 +//
35.18 +// The above copyright notice and this permission notice shall be included
35.19 +// in all copies or substantial portions of the Software.
35.20 +//
35.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
35.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
35.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
35.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
35.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
35.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
35.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
35.28 +// </copyright>
35.29 +// <summary>
35.30 +// Represents an axis with logarithmic scale.
35.31 +// </summary>
35.32 +// --------------------------------------------------------------------------------------------------------------------
35.33 +namespace OxyPlot.Axes
35.34 +{
35.35 + using System;
35.36 + using System.Collections.Generic;
35.37 + using System.Diagnostics;
35.38 +
35.39 + /// <summary>
35.40 + /// Represents an axis with logarithmic scale.
35.41 + /// </summary>
35.42 + /// <remarks>
35.43 + /// See http://en.wikipedia.org/wiki/Logarithmic_scale.
35.44 + /// </remarks>
35.45 + public class LogarithmicAxis : Axis
35.46 + {
35.47 + /// <summary>
35.48 + /// Initializes a new instance of the <see cref = "LogarithmicAxis" /> class.
35.49 + /// </summary>
35.50 + public LogarithmicAxis()
35.51 + {
35.52 + this.PowerPadding = true;
35.53 + this.Base = 10;
35.54 + this.FilterMinValue = 0;
35.55 + }
35.56 +
35.57 + /// <summary>
35.58 + /// Initializes a new instance of the <see cref="LogarithmicAxis"/> class.
35.59 + /// </summary>
35.60 + /// <param name="pos">
35.61 + /// The position.
35.62 + /// </param>
35.63 + /// <param name="title">
35.64 + /// The title.
35.65 + /// </param>
35.66 + public LogarithmicAxis(AxisPosition pos, string title)
35.67 + : this()
35.68 + {
35.69 + this.Position = pos;
35.70 + this.Title = title;
35.71 + }
35.72 +
35.73 + /// <summary>
35.74 + /// Initializes a new instance of the <see cref="LogarithmicAxis"/> class.
35.75 + /// </summary>
35.76 + /// <param name="position">
35.77 + /// The position.
35.78 + /// </param>
35.79 + /// <param name="minimum">
35.80 + /// The minimum.
35.81 + /// </param>
35.82 + /// <param name="maximum">
35.83 + /// The maximum.
35.84 + /// </param>
35.85 + /// <param name="title">
35.86 + /// The title.
35.87 + /// </param>
35.88 + public LogarithmicAxis(
35.89 + AxisPosition position, double minimum = double.NaN, double maximum = double.NaN, string title = null)
35.90 + : this()
35.91 + {
35.92 + this.Position = position;
35.93 + this.Title = title;
35.94 + this.Minimum = minimum;
35.95 + this.Maximum = maximum;
35.96 + }
35.97 +
35.98 + /// <summary>
35.99 + /// Gets or sets the logarithmic base (normally 10).
35.100 + /// </summary>
35.101 + /// <remarks>
35.102 + /// See http://en.wikipedia.org/wiki/Logarithm.
35.103 + /// </remarks>
35.104 + /// <value>The logarithmic base.</value>
35.105 + public double Base { get; set; }
35.106 +
35.107 + /// <summary>
35.108 + /// Gets or sets a value indicating whether the ActualMaximum and ActualMinimum values should be padded to the nearest power of the Base.
35.109 + /// </summary>
35.110 + public bool PowerPadding { get; set; }
35.111 +
35.112 + /// <summary>
35.113 + /// Coerces the actual maximum and minimum values.
35.114 + /// </summary>
35.115 + public override void CoerceActualMaxMin()
35.116 + {
35.117 + if (double.IsNaN(this.ActualMinimum) || double.IsInfinity(this.ActualMinimum))
35.118 + {
35.119 + this.ActualMinimum = 1;
35.120 + }
35.121 +
35.122 + if (this.ActualMinimum <= 0)
35.123 + {
35.124 + this.ActualMinimum = 1;
35.125 + }
35.126 +
35.127 + if (this.ActualMaximum <= this.ActualMinimum)
35.128 + {
35.129 + this.ActualMaximum = this.ActualMinimum * 100;
35.130 + }
35.131 +
35.132 + base.CoerceActualMaxMin();
35.133 + }
35.134 +
35.135 + /// <summary>
35.136 + /// Gets the coordinates used to draw ticks and tick labels (numbers or category names).
35.137 + /// </summary>
35.138 + /// <param name="majorLabelValues">
35.139 + /// The major label values.
35.140 + /// </param>
35.141 + /// <param name="majorTickValues">
35.142 + /// The major tick values.
35.143 + /// </param>
35.144 + /// <param name="minorTickValues">
35.145 + /// The minor tick values.
35.146 + /// </param>
35.147 + public override void GetTickValues(
35.148 + out IList<double> majorLabelValues, out IList<double> majorTickValues, out IList<double> minorTickValues)
35.149 + {
35.150 + if (this.ActualMinimum <= 0)
35.151 + {
35.152 + this.ActualMinimum = 0.1;
35.153 + }
35.154 +
35.155 + double logBase = Math.Log(this.Base);
35.156 + var e0 = (int)Math.Floor(Math.Log(this.ActualMinimum) / logBase);
35.157 + var e1 = (int)Math.Ceiling(Math.Log(this.ActualMaximum) / logBase);
35.158 +
35.159 + // find the min & max values for the specified base
35.160 + // round to max 10 digits
35.161 + double p0 = Math.Pow(this.Base, e0);
35.162 + double p1 = Math.Pow(this.Base, e1);
35.163 + double d0 = Math.Round(p0, 10);
35.164 + double d1 = Math.Round(p1, 10);
35.165 + if (d0 <= 0)
35.166 + {
35.167 + d0 = p0;
35.168 + }
35.169 +
35.170 + double d = d0;
35.171 + majorTickValues = new List<double>();
35.172 + minorTickValues = new List<double>();
35.173 +
35.174 + double epsMin = this.ActualMinimum * 1e-6;
35.175 + double epsMax = this.ActualMaximum * 1e-6;
35.176 +
35.177 + while (d <= d1 + epsMax)
35.178 + {
35.179 + // d = RemoveNoiseFromDoubleMath(d);
35.180 + if (d >= this.ActualMinimum - epsMin && d <= this.ActualMaximum + epsMax)
35.181 + {
35.182 + majorTickValues.Add(d);
35.183 + }
35.184 +
35.185 + for (int i = 1; i < this.Base; i++)
35.186 + {
35.187 + double d2 = d * (i + 1);
35.188 + if (d2 > d1 + double.Epsilon)
35.189 + {
35.190 + break;
35.191 + }
35.192 +
35.193 + if (d2 > this.ActualMaximum)
35.194 + {
35.195 + break;
35.196 + }
35.197 +
35.198 + if (d2 >= this.ActualMinimum && d2 <= this.ActualMaximum)
35.199 + {
35.200 + minorTickValues.Add(d2);
35.201 + }
35.202 + }
35.203 +
35.204 + d *= this.Base;
35.205 + if (double.IsInfinity(d))
35.206 + {
35.207 + break;
35.208 + }
35.209 +
35.210 + if (d < double.Epsilon)
35.211 + {
35.212 + break;
35.213 + }
35.214 +
35.215 + if (double.IsNaN(d))
35.216 + {
35.217 + break;
35.218 + }
35.219 + }
35.220 +
35.221 + if (majorTickValues.Count < 2)
35.222 + {
35.223 + base.GetTickValues(out majorLabelValues, out majorTickValues, out minorTickValues);
35.224 + }
35.225 + else
35.226 + {
35.227 + majorLabelValues = majorTickValues;
35.228 + }
35.229 + }
35.230 +
35.231 + /// <summary>
35.232 + /// Determines whether the specified value is valid.
35.233 + /// </summary>
35.234 + /// <param name="value">
35.235 + /// The value.
35.236 + /// </param>
35.237 + /// <returns>
35.238 + /// <c>true</c> if the specified value is valid; otherwise, <c>false</c>.
35.239 + /// </returns>
35.240 + public override bool IsValidValue(double value)
35.241 + {
35.242 + return value > 0 && base.IsValidValue(value);
35.243 + }
35.244 +
35.245 + /// <summary>
35.246 + /// Determines whether the axis is used for X/Y values.
35.247 + /// </summary>
35.248 + /// <returns>
35.249 + /// <c>true</c> if it is an XY axis; otherwise, <c>false</c> .
35.250 + /// </returns>
35.251 + public override bool IsXyAxis()
35.252 + {
35.253 + return true;
35.254 + }
35.255 +
35.256 + /// <summary>
35.257 + /// Pans the specified axis.
35.258 + /// </summary>
35.259 + /// <param name="ppt">
35.260 + /// The previous point (screen coordinates).
35.261 + /// </param>
35.262 + /// <param name="cpt">
35.263 + /// The current point (screen coordinates).
35.264 + /// </param>
35.265 + public override void Pan(ScreenPoint ppt, ScreenPoint cpt)
35.266 + {
35.267 + if (!this.IsPanEnabled)
35.268 + {
35.269 + return;
35.270 + }
35.271 +
35.272 + bool isHorizontal = this.IsHorizontal();
35.273 +
35.274 + double x0 = this.InverseTransform(isHorizontal ? ppt.X : ppt.Y);
35.275 + double x1 = this.InverseTransform(isHorizontal ? cpt.X : cpt.Y);
35.276 +
35.277 + if (Math.Abs(x1) < double.Epsilon)
35.278 + {
35.279 + return;
35.280 + }
35.281 +
35.282 + double dx = x0 / x1;
35.283 +
35.284 + double newMinimum = this.ActualMinimum * dx;
35.285 + double newMaximum = this.ActualMaximum * dx;
35.286 + if (newMinimum < this.AbsoluteMinimum)
35.287 + {
35.288 + newMinimum = this.AbsoluteMinimum;
35.289 + newMaximum = newMinimum * this.ActualMaximum / this.ActualMinimum;
35.290 + }
35.291 +
35.292 + if (newMaximum > this.AbsoluteMaximum)
35.293 + {
35.294 + newMaximum = this.AbsoluteMaximum;
35.295 + newMinimum = newMaximum * this.ActualMaximum / this.ActualMinimum;
35.296 + }
35.297 +
35.298 + this.ViewMinimum = newMinimum;
35.299 + this.ViewMaximum = newMaximum;
35.300 +
35.301 + this.OnAxisChanged(new AxisChangedEventArgs(AxisChangeTypes.Pan));
35.302 + }
35.303 +
35.304 + /// <summary>
35.305 + /// Transforms the specified coordinate to screen coordinates.
35.306 + /// </summary>
35.307 + /// <param name="x">
35.308 + /// The value.
35.309 + /// </param>
35.310 + /// <returns>
35.311 + /// The transformed value (screen coordinate).
35.312 + /// </returns>
35.313 + public override double Transform(double x)
35.314 + {
35.315 + Debug.Assert(x > 0, "Value should be positive.");
35.316 + if (x <= 0)
35.317 + {
35.318 + return -1;
35.319 + }
35.320 +
35.321 + return (Math.Log(x) - this.offset) * this.scale;
35.322 + }
35.323 +
35.324 + /// <summary>
35.325 + /// Zooms the axis at the specified coordinate.
35.326 + /// </summary>
35.327 + /// <param name="factor">
35.328 + /// The zoom factor.
35.329 + /// </param>
35.330 + /// <param name="x">
35.331 + /// The coordinate to zoom at.
35.332 + /// </param>
35.333 + public override void ZoomAt(double factor, double x)
35.334 + {
35.335 + if (!this.IsZoomEnabled)
35.336 + {
35.337 + return;
35.338 + }
35.339 +
35.340 + double px = this.PreTransform(x);
35.341 + double dx0 = this.PreTransform(this.ActualMinimum) - px;
35.342 + double dx1 = this.PreTransform(this.ActualMaximum) - px;
35.343 + double newViewMinimum = this.PostInverseTransform((dx0 / factor) + px);
35.344 + double newViewMaximum = this.PostInverseTransform((dx1 / factor) + px);
35.345 +
35.346 + this.ViewMinimum = Math.Max(newViewMinimum, this.AbsoluteMinimum);
35.347 + this.ViewMaximum = Math.Min(newViewMaximum, this.AbsoluteMaximum);
35.348 + }
35.349 +
35.350 + /// <summary>
35.351 + /// Applies a transformation after the inverse transform of the value. This is used in logarithmic axis.
35.352 + /// </summary>
35.353 + /// <param name="x">The value to transform.</param>
35.354 + /// <returns>
35.355 + /// The transformed value.
35.356 + /// </returns>
35.357 + internal override double PostInverseTransform(double x)
35.358 + {
35.359 + return Math.Exp(x);
35.360 + }
35.361 +
35.362 + /// <summary>
35.363 + /// Applies a transformation before the transform the value. This is used in logarithmic axis.
35.364 + /// </summary>
35.365 + /// <param name="x">The value to transform.</param>
35.366 + /// <returns>
35.367 + /// The transformed value.
35.368 + /// </returns>
35.369 + internal override double PreTransform(double x)
35.370 + {
35.371 + Debug.Assert(x > 0, "Value should be positive.");
35.372 +
35.373 + if (x <= 0)
35.374 + {
35.375 + return 0;
35.376 + }
35.377 +
35.378 + return Math.Log(x);
35.379 + }
35.380 +
35.381 + /// <summary>
35.382 + /// Updates the actual maximum and minimum values.
35.383 + /// If the user has zoomed/panned the axis, the internal ViewMaximum/ViewMinimum values will be used.
35.384 + /// If Maximum or Minimum have been set, these values will be used.
35.385 + /// Otherwise the maximum and minimum values of the series will be used, including the 'padding'.
35.386 + /// </summary>
35.387 + internal override void UpdateActualMaxMin()
35.388 + {
35.389 + if (this.PowerPadding)
35.390 + {
35.391 + double logBase = Math.Log(this.Base);
35.392 + var e0 = (int)Math.Floor(Math.Log(this.ActualMinimum) / logBase);
35.393 + var e1 = (int)Math.Ceiling(Math.Log(this.ActualMaximum) / logBase);
35.394 + if (!double.IsNaN(this.ActualMinimum))
35.395 + {
35.396 + this.ActualMinimum = Math.Exp(e0 * logBase).RemoveNoiseFromDoubleMath();
35.397 + }
35.398 +
35.399 + if (!double.IsNaN(this.ActualMaximum))
35.400 + {
35.401 + this.ActualMaximum = Math.Exp(e1 * logBase).RemoveNoiseFromDoubleMath();
35.402 + }
35.403 + }
35.404 +
35.405 + base.UpdateActualMaxMin();
35.406 + }
35.407 +
35.408 + }
35.409 +}
35.410 \ No newline at end of file
36.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
36.2 +++ b/External/OxyPlot/OxyPlot/Axes/MagnitudeAxis.cs Sat Jun 08 16:53:22 2013 +0000
36.3 @@ -0,0 +1,205 @@
36.4 +// --------------------------------------------------------------------------------------------------------------------
36.5 +// <copyright file="MagnitudeAxis.cs" company="OxyPlot">
36.6 +// The MIT License (MIT)
36.7 +//
36.8 +// Copyright (c) 2012 Oystein Bjorke
36.9 +//
36.10 +// Permission is hereby granted, free of charge, to any person obtaining a
36.11 +// copy of this software and associated documentation files (the
36.12 +// "Software"), to deal in the Software without restriction, including
36.13 +// without limitation the rights to use, copy, modify, merge, publish,
36.14 +// distribute, sublicense, and/or sell copies of the Software, and to
36.15 +// permit persons to whom the Software is furnished to do so, subject to
36.16 +// the following conditions:
36.17 +//
36.18 +// The above copyright notice and this permission notice shall be included
36.19 +// in all copies or substantial portions of the Software.
36.20 +//
36.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
36.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
36.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
36.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
36.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
36.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
36.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
36.28 +// </copyright>
36.29 +// <summary>
36.30 +// Represents a magnitude axis for polar plots.
36.31 +// </summary>
36.32 +// --------------------------------------------------------------------------------------------------------------------
36.33 +namespace OxyPlot.Axes
36.34 +{
36.35 + using System;
36.36 +
36.37 + /// <summary>
36.38 + /// Represents a magnitude axis for polar plots.
36.39 + /// </summary>
36.40 + public class MagnitudeAxis : LinearAxis
36.41 + {
36.42 + /// <summary>
36.43 + /// Initializes a new instance of the <see cref="MagnitudeAxis"/> class.
36.44 + /// </summary>
36.45 + public MagnitudeAxis()
36.46 + {
36.47 + this.Position = AxisPosition.Bottom;
36.48 + this.IsPanEnabled = false;
36.49 + this.IsZoomEnabled = false;
36.50 +
36.51 + this.MajorGridlineStyle = LineStyle.Solid;
36.52 + this.MinorGridlineStyle = LineStyle.Solid;
36.53 + }
36.54 +
36.55 + /// <summary>
36.56 + /// Initializes a new instance of the <see cref="MagnitudeAxis"/> class.
36.57 + /// </summary>
36.58 + /// <param name="minimum">
36.59 + /// The minimum.
36.60 + /// </param>
36.61 + /// <param name="maximum">
36.62 + /// The maximum.
36.63 + /// </param>
36.64 + /// <param name="majorStep">
36.65 + /// The major step.
36.66 + /// </param>
36.67 + /// <param name="minorStep">
36.68 + /// The minor step.
36.69 + /// </param>
36.70 + /// <param name="title">
36.71 + /// The title.
36.72 + /// </param>
36.73 + public MagnitudeAxis(
36.74 + double minimum = double.NaN,
36.75 + double maximum = double.NaN,
36.76 + double majorStep = double.NaN,
36.77 + double minorStep = double.NaN,
36.78 + string title = null)
36.79 + : this()
36.80 + {
36.81 + this.Minimum = minimum;
36.82 + this.Maximum = maximum;
36.83 + this.MajorStep = majorStep;
36.84 + this.MinorStep = minorStep;
36.85 + this.Title = title;
36.86 + }
36.87 +
36.88 + /// <summary>
36.89 + /// Gets or sets the midpoint (screen coordinates) of the plot area. This is used by polar coordinate systems.
36.90 + /// </summary>
36.91 + internal ScreenPoint MidPoint { get; set; }
36.92 +
36.93 + /// <summary>
36.94 + /// Inverse transform the specified screen point.
36.95 + /// </summary>
36.96 + /// <param name="x">
36.97 + /// The x coordinate.
36.98 + /// </param>
36.99 + /// <param name="y">
36.100 + /// The y coordinate.
36.101 + /// </param>
36.102 + /// <param name="yaxis">
36.103 + /// The y-axis.
36.104 + /// </param>
36.105 + /// <returns>
36.106 + /// The data point.
36.107 + /// </returns>
36.108 + public override DataPoint InverseTransform(double x, double y, Axis yaxis)
36.109 + {
36.110 + var angleAxis = yaxis as AngleAxis;
36.111 + if (angleAxis == null)
36.112 + {
36.113 + throw new InvalidOperationException("Polar angle axis not defined!");
36.114 + }
36.115 +
36.116 + x -= this.MidPoint.x;
36.117 + y -= this.MidPoint.y;
36.118 + double th = Math.Atan2(y, x);
36.119 + double r = Math.Sqrt((x * x) + (y * y));
36.120 + x = (r / this.scale) + this.offset;
36.121 + y = (th / angleAxis.Scale) + angleAxis.Offset;
36.122 + return new DataPoint(x, y);
36.123 + }
36.124 +
36.125 + /// <summary>
36.126 + /// Determines whether the axis is used for X/Y values.
36.127 + /// </summary>
36.128 + /// <returns>
36.129 + /// <c>true</c> if it is an XY axis; otherwise, <c>false</c> .
36.130 + /// </returns>
36.131 + public override bool IsXyAxis()
36.132 + {
36.133 + return false;
36.134 + }
36.135 +
36.136 + /// <summary>
36.137 + /// Renders the axis on the specified render context.
36.138 + /// </summary>
36.139 + /// <param name="rc">The render context.</param>
36.140 + /// <param name="model">The model.</param>
36.141 + /// <param name="axisLayer">The rendering order.</param>
36.142 + /// <param name="pass"></param>
36.143 + public override void Render(IRenderContext rc, PlotModel model, AxisLayer axisLayer, int pass)
36.144 + {
36.145 + if (this.Layer != axisLayer)
36.146 + {
36.147 + return;
36.148 + }
36.149 +
36.150 + var r = new MagnitudeAxisRenderer(rc, model);
36.151 + r.Render(this, pass);
36.152 + }
36.153 +
36.154 + /// <summary>
36.155 + /// Transforms the specified point to screen coordinates.
36.156 + /// </summary>
36.157 + /// <param name="x">
36.158 + /// The x value (for the current axis).
36.159 + /// </param>
36.160 + /// <param name="y">
36.161 + /// The y value.
36.162 + /// </param>
36.163 + /// <param name="yaxis">
36.164 + /// The y axis.
36.165 + /// </param>
36.166 + /// <returns>
36.167 + /// The transformed point.
36.168 + /// </returns>
36.169 + public override ScreenPoint Transform(double x, double y, Axis yaxis)
36.170 + {
36.171 + var angleAxis = yaxis as AngleAxis;
36.172 + if (angleAxis == null)
36.173 + {
36.174 + throw new InvalidOperationException("Polar angle axis not defined!");
36.175 + }
36.176 +
36.177 + double r = (x - this.Offset) * this.scale;
36.178 + double theta = (y - angleAxis.Offset) * angleAxis.Scale;
36.179 +
36.180 + return new ScreenPoint(this.MidPoint.x + (r * Math.Cos(theta)), this.MidPoint.y - (r * Math.Sin(theta)));
36.181 + }
36.182 +
36.183 + /// <summary>
36.184 + /// Updates the scale and offset properties of the transform from the specified boundary rectangle.
36.185 + /// </summary>
36.186 + /// <param name="bounds">
36.187 + /// The bounds.
36.188 + /// </param>
36.189 + internal override void UpdateTransform(OxyRect bounds)
36.190 + {
36.191 + double x0 = bounds.Left;
36.192 + double x1 = bounds.Right;
36.193 + double y0 = bounds.Bottom;
36.194 + double y1 = bounds.Top;
36.195 +
36.196 + this.ScreenMin = new ScreenPoint(x0, y1);
36.197 + this.ScreenMax = new ScreenPoint(x1, y0);
36.198 +
36.199 + this.MidPoint = new ScreenPoint((x0 + x1) / 2, (y0 + y1) / 2);
36.200 +
36.201 + this.ActualMinimum = 0;
36.202 + double r = Math.Min(Math.Abs(x1 - x0), Math.Abs(y1 - y0));
36.203 + this.scale = 0.5 * r / (this.ActualMaximum - this.ActualMinimum);
36.204 + this.Offset = this.ActualMinimum;
36.205 + }
36.206 +
36.207 + }
36.208 +}
36.209 \ No newline at end of file
37.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
37.2 +++ b/External/OxyPlot/OxyPlot/Axes/RangeAxis.cs Sat Jun 08 16:53:22 2013 +0000
37.3 @@ -0,0 +1,469 @@
37.4 +// --------------------------------------------------------------------------------------------------------------------
37.5 +// <copyright file="RangeAxis.cs" company="OxyPlot">
37.6 +// The MIT License (MIT)
37.7 +//
37.8 +// Copyright (c) 2012 Oystein Bjorke
37.9 +//
37.10 +// Permission is hereby granted, free of charge, to any person obtaining a
37.11 +// copy of this software and associated documentation files (the
37.12 +// "Software"), to deal in the Software without restriction, including
37.13 +// without limitation the rights to use, copy, modify, merge, publish,
37.14 +// distribute, sublicense, and/or sell copies of the Software, and to
37.15 +// permit persons to whom the Software is furnished to do so, subject to
37.16 +// the following conditions:
37.17 +//
37.18 +// The above copyright notice and this permission notice shall be included
37.19 +// in all copies or substantial portions of the Software.
37.20 +//
37.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
37.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
37.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
37.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
37.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
37.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
37.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
37.28 +// </copyright>
37.29 +// <summary>
37.30 +// Updates the minor/major step intervals if they are undefined.
37.31 +// </summary>
37.32 +// --------------------------------------------------------------------------------------------------------------------
37.33 +using System;
37.34 +using System.Collections.Generic;
37.35 +using System.Collections.ObjectModel;
37.36 +using System.Diagnostics;
37.37 +using System.Globalization;
37.38 +
37.39 +namespace OxyPlot
37.40 +{
37.41 + public class Axis : IAxis
37.42 + {
37.43 + public Axis()
37.44 + {
37.45 + Position = AxisPosition.Left;
37.46 + IsVisible = true;
37.47 +
37.48 + Minimum = double.NaN;
37.49 + Maximum = double.NaN;
37.50 + MinorStep = double.NaN;
37.51 + MajorStep = double.NaN;
37.52 +
37.53 + MinimumPadding = 0.01;
37.54 + MaximumPadding = 0.01;
37.55 +
37.56 + TickStyle = TickStyle.Inside;
37.57 + MajorGridlineStyle = LineStyle.None;
37.58 + MinorGridlineStyle = LineStyle.None;
37.59 + TicklineColor = Colors.Black;
37.60 + MajorGridlineColor = Color.FromARGB(0x40, 0, 0, 0);
37.61 + TicklineColor = Colors.Black;
37.62 + MinorGridlineColor = Color.FromARGB(0x20, 0, 0, 0x00);
37.63 + MajorGridlineThickness = 1;
37.64 + MinorGridlineThickness = 1;
37.65 +
37.66 + ExtraGridlineStyle = LineStyle.Solid;
37.67 + ExtraGridlineColor = Colors.Black;
37.68 + ExtraGridlineThickness = 1;
37.69 +
37.70 + ShowMinorTicks = true;
37.71 +
37.72 + FontFamily = "Segoe UI";
37.73 + FontSize = 12;
37.74 +
37.75 + MinorTickSize = 4;
37.76 + MajorTickSize = 7;
37.77 +
37.78 + StartPosition = 0;
37.79 + EndPosition = 1;
37.80 +
37.81 + Angle = 0;
37.82 + }
37.83 +
37.84 + public Axis(AxisPosition pos, double minimum, double maximum)
37.85 + : this()
37.86 + {
37.87 + Position = pos;
37.88 + Minimum = minimum;
37.89 + Maximum = maximum;
37.90 + }
37.91 + public string Key { get; set; }
37.92 +
37.93 + public AxisPosition Position { get; set; }
37.94 + public bool PositionAtZeroCrossing { get; set; }
37.95 + public bool IsHorizontal { get { return Position == AxisPosition.Top || Position == AxisPosition.Bottom; } }
37.96 + public bool IsVertical { get { return Position == AxisPosition.Left || Position == AxisPosition.Right; } }
37.97 + public bool IsPolar { get { return Position == AxisPosition.Magnitude || Position == AxisPosition.Angle; } }
37.98 +
37.99 + public bool IsVisible { get; set; }
37.100 +
37.101 + public double ActualMinimum { get; set; }
37.102 + public double ActualMaximum { get; set; }
37.103 + internal double ActualMinorStep { get; set; }
37.104 + internal double ActualMajorStep { get; set; }
37.105 +
37.106 + public double Minimum { get; set; }
37.107 + public double Maximum { get; set; }
37.108 + public double MinorStep { get; set; }
37.109 + public double MajorStep { get; set; }
37.110 +
37.111 + public double MinimumPadding { get; set; }
37.112 + public double MaximumPadding { get; set; }
37.113 +
37.114 + public TickStyle TickStyle { get; set; }
37.115 + public double MinorTickSize { get; set; }
37.116 + public double MajorTickSize { get; set; }
37.117 + public Color TicklineColor { get; set; }
37.118 + public bool ShowMinorTicks { get; set; }
37.119 +
37.120 + public LineStyle MajorGridlineStyle { get; set; }
37.121 + public LineStyle MinorGridlineStyle { get; set; }
37.122 + public Color MajorGridlineColor { get; set; }
37.123 + public Color MinorGridlineColor { get; set; }
37.124 + public double MajorGridlineThickness { get; set; }
37.125 + public double MinorGridlineThickness { get; set; }
37.126 +
37.127 + public double[] ExtraGridlines { get; set; }
37.128 + public LineStyle ExtraGridlineStyle { get; set; }
37.129 + public Color ExtraGridlineColor { get; set; }
37.130 + public double ExtraGridlineThickness { get; set; }
37.131 +
37.132 + public double Angle { get; set; }
37.133 + public string StringFormat { get; set; }
37.134 + internal string ActualStringFormat { get; set; }
37.135 + public string Title { get; set; }
37.136 + public string Unit { get; set; }
37.137 +
37.138 + public string FontFamily { get; set; }
37.139 + public double FontSize { get; set; }
37.140 + public double FontWeight { get; set; }
37.141 +
37.142 + public double StartPosition { get; set; }
37.143 + public double EndPosition { get; set; }
37.144 +
37.145 + public Axis RelatedAxis { get; set; }
37.146 +
37.147 + public bool IsReversed { get { return StartPosition > EndPosition; } }
37.148 +
37.149 + internal double Offset;
37.150 + internal double Scale;
37.151 + internal Point MidPoint;
37.152 + internal Point ScreenMin;
37.153 + internal Point ScreenMax;
37.154 +
37.155 + public override string ToString()
37.156 + {
37.157 + return String.Format(CultureInfo.InvariantCulture, "{0}({1}, {2}, {3}, {4})", GetType().Name, Position, ActualMinimum, ActualMaximum, ActualMajorStep);
37.158 + }
37.159 +
37.160 + public virtual void GetTickValues(out ICollection<double> majorValues, out ICollection<double> minorValues)
37.161 + {
37.162 + minorValues = CreateTickValues(ActualMinimum, ActualMaximum, ActualMinorStep);
37.163 + majorValues = CreateTickValues(ActualMinimum, ActualMaximum, ActualMajorStep);
37.164 + }
37.165 +
37.166 + public virtual string FormatValue(double x)
37.167 + {
37.168 + return x.ToString(ActualStringFormat, CultureInfo.InvariantCulture);
37.169 + }
37.170 +
37.171 + private static ICollection<double> CreateTickValues(double min, double max, double step)
37.172 + {
37.173 + if (max <= min)
37.174 + throw new InvalidOperationException("Axis: Maximum should be larger than minimum.");
37.175 + if (step <= 0)
37.176 + throw new InvalidOperationException("Axis: Step cannot be negative.");
37.177 +
37.178 + double x = (int)Math.Round(min / step) * step;
37.179 +
37.180 + var values = new Collection<double>();
37.181 + // Maximum number of iterations (in case of very small step size)
37.182 + int it = 0;
37.183 + const int maxit = 1000;
37.184 + double epsilon = Math.Abs(max - min) * 1e-6;
37.185 + while (x <= max + epsilon && it++ < maxit)
37.186 + {
37.187 + if (x >= min - epsilon && x <= max + epsilon)
37.188 + {
37.189 + x = RemoveNoiseFromDoubleMath(x);
37.190 + values.Add(x);
37.191 + }
37.192 + x += step;
37.193 + }
37.194 + return values;
37.195 + }
37.196 +
37.197 + protected virtual double PreTransform(double x)
37.198 + {
37.199 + return x;
37.200 + }
37.201 +
37.202 + protected virtual double PostInverseTransform(double x)
37.203 + {
37.204 + return x;
37.205 + }
37.206 +
37.207 + public virtual Point Transform(double x, double y, Axis yAxis)
37.208 + {
37.209 + Debug.Assert(yAxis != null);
37.210 + if (IsPolar)
37.211 + {
37.212 + double r = (x - Offset) * Scale;
37.213 + double th = yAxis != null ? (y - yAxis.Offset) * yAxis.Scale : double.NaN;
37.214 + return new Point(MidPoint.X + r * Math.Cos(th), MidPoint.Y + r * Math.Sin(th));
37.215 + }
37.216 + if (yAxis == null)
37.217 + return new Point();
37.218 + return new Point(TransformX(x), yAxis != null ? yAxis.TransformX(y) : double.NaN);
37.219 + }
37.220 +
37.221 + public double TransformX(double x)
37.222 + {
37.223 + return (PreTransform(x) - Offset) * Scale;
37.224 + }
37.225 +
37.226 + public virtual Point InverseTransform(double x, double y, Axis yAxis)
37.227 + {
37.228 + Debug.Assert(yAxis != null);
37.229 + if (IsPolar)
37.230 + {
37.231 + x -= MidPoint.X;
37.232 + y -= MidPoint.Y;
37.233 + double th = Math.Atan2(y, x);
37.234 + double r = Math.Sqrt(x * x + y * y);
37.235 + x = r / Scale + Offset;
37.236 + y = yAxis != null ? th / yAxis.Scale + yAxis.Offset : double.NaN;
37.237 + return new Point(x, y);
37.238 + }
37.239 +
37.240 + return new Point(InverseTransformX(x), yAxis.InverseTransformX(y));
37.241 + }
37.242 +
37.243 + public double InverseTransformX(double x)
37.244 + {
37.245 + return PostInverseTransform(x / Scale + Offset);
37.246 + }
37.247 +
37.248 + public double UpdateTransform(double x0, double x1, double y0, double y1)
37.249 + {
37.250 + ScreenMin = new Point(x0, y1);
37.251 + ScreenMax = new Point(x1, y0);
37.252 +
37.253 + if (Position == AxisPosition.Angle)
37.254 + {
37.255 + MidPoint = new Point((x0 + x1) / 2, (y0 + y1) / 2);
37.256 + Scale = 2 * Math.PI / (ActualMaximum - ActualMinimum);
37.257 + Offset = ActualMinimum;
37.258 + return Scale;
37.259 + }
37.260 + if (Position == AxisPosition.Magnitude)
37.261 + {
37.262 + ActualMinimum = 0;
37.263 + MidPoint = new Point((x0 + x1) / 2, (y0 + y1) / 2);
37.264 + double r = Math.Min(Math.Abs(x1 - x0), Math.Abs(y1 - y0));
37.265 + Scale = 0.5 * r / (ActualMaximum - ActualMinimum);
37.266 + Offset = ActualMinimum;
37.267 + return Scale;
37.268 + }
37.269 + double a0 = IsHorizontal ? x0 : y0;
37.270 + double a1 = IsHorizontal ? x1 : y1;
37.271 +
37.272 + double dx = a1 - a0;
37.273 + a1 = a0 + EndPosition * dx;
37.274 + a0 = a0 + StartPosition * dx;
37.275 +
37.276 + if (ActualMaximum - ActualMinimum < double.Epsilon)
37.277 + ActualMaximum = ActualMinimum + 1;
37.278 +
37.279 + double max = PreTransform(ActualMaximum);
37.280 + double min = PreTransform(ActualMinimum);
37.281 +
37.282 + const double eps = 1e-6;
37.283 + if (max - min < eps) max = min + 1;
37.284 +
37.285 + if (Math.Abs(a0 - a1) != 0)
37.286 + Offset = (a0 * max - min * a1) / (a0 - a1);
37.287 + else
37.288 + Offset = 0;
37.289 +
37.290 + Scale = (a1 - a0) / (max - min);
37.291 +
37.292 + return Scale;
37.293 + }
37.294 +
37.295 + public void SetScale(double scale)
37.296 + {
37.297 + double sgn = Math.Sign(Scale);
37.298 + double mid = (ActualMaximum + ActualMinimum) / 2;
37.299 + double dx = (Offset - mid) * Scale;
37.300 + Scale = sgn * scale;
37.301 + Offset = dx / Scale + mid;
37.302 + }
37.303 +
37.304 + public virtual void Pan(double dx)
37.305 + {
37.306 + Minimum = ActualMinimum + dx;
37.307 + Maximum = ActualMaximum + dx;
37.308 + }
37.309 +
37.310 + public virtual void ScaleAt(double factor, double x)
37.311 + {
37.312 + double dx0 = (ActualMinimum - x) * Scale;
37.313 + double dx1 = (ActualMaximum - x) * Scale;
37.314 + Scale *= factor;
37.315 + Minimum = dx0 / Scale + x;
37.316 + Maximum = dx1 / Scale + x;
37.317 + }
37.318 +
37.319 + public virtual void Zoom(double x0, double x1)
37.320 + {
37.321 + Minimum = Math.Min(x0, x1);
37.322 + Maximum = Math.Max(x0, x1);
37.323 + }
37.324 +
37.325 + public virtual void Reset()
37.326 + {
37.327 + Minimum = double.NaN;
37.328 + Maximum = double.NaN;
37.329 + }
37.330 +
37.331 + /// <summary>
37.332 + /// Updates the minor/major step intervals if they are undefined.
37.333 + /// </summary>
37.334 + public void UpdateIntervals(double dx, double dy)
37.335 + {
37.336 + double labelSize = GetLabelSize();
37.337 + double length = IsHorizontal ? dx : dy;
37.338 +
37.339 + if (!double.IsNaN(MajorStep))
37.340 + ActualMajorStep = MajorStep;
37.341 + else
37.342 + ActualMajorStep = CalculateActualInterval(length, labelSize);
37.343 +
37.344 + if (!double.IsNaN(MinorStep))
37.345 + ActualMinorStep = MinorStep;
37.346 + else
37.347 + ActualMinorStep = ActualMajorStep / 5;
37.348 +
37.349 + if (double.IsNaN(ActualMinorStep))
37.350 + ActualMinorStep = 2;
37.351 + if (double.IsNaN(ActualMajorStep))
37.352 + ActualMajorStep = 10;
37.353 +
37.354 + ActualStringFormat = StringFormat;
37.355 + }
37.356 +
37.357 + private double GetLabelSize()
37.358 + {
37.359 + if (IsHorizontal)
37.360 + return 100;
37.361 + if (IsVertical)
37.362 + return 30;
37.363 + if (Position == AxisPosition.Angle)
37.364 + return 50;
37.365 + if (Position == AxisPosition.Magnitude)
37.366 + return 100;
37.367 + return 50;
37.368 + }
37.369 +
37.370 + protected virtual double CalculateActualInterval(double availableSize, double maxIntervalSize)
37.371 + {
37.372 + return CalculateActualInterval2(availableSize, maxIntervalSize);
37.373 + }
37.374 +
37.375 + private double CalculateActualInterval1(double availableSize, double maxIntervalSize)
37.376 + {
37.377 + int minTags = 5;
37.378 + int maxTags = 20;
37.379 + int numberOfTags = (int)(availableSize / maxIntervalSize);
37.380 + double range = ActualMaximum - ActualMinimum;
37.381 + double interval = range / numberOfTags;
37.382 + const int k1 = 10;
37.383 + interval = Math.Log10(interval / k1);
37.384 + interval = Math.Ceiling(interval);
37.385 + interval = Math.Pow(10, interval) * k1;
37.386 +
37.387 + if (range / interval > maxTags) interval *= 5;
37.388 + if (range / interval < minTags) interval *= 0.5;
37.389 +
37.390 + if (interval <= 0) interval = 1;
37.391 + return interval;
37.392 + }
37.393 +
37.394 + /// <summary>
37.395 + /// Returns the actual interval to use to determine which values are
37.396 + /// displayed in the axis.
37.397 + /// </summary>
37.398 + /// <param name="availableSize">The available size.</param>
37.399 + /// <returns>Actual interval to use to determine which values are
37.400 + /// displayed in the axis.
37.401 + /// </returns>
37.402 + private double CalculateActualInterval2(double availableSize, double maxIntervalSize)
37.403 + {
37.404 + Func<double, double> Exponent = x => Math.Ceiling(Math.Log(x, 10));
37.405 + Func<double, double> Mantissa = x => x / Math.Pow(10, Exponent(x) - 1);
37.406 +
37.407 + // reduce intervals for horizontal axis.
37.408 + // double maxIntervals = Orientation == AxisOrientation.X ? MaximumAxisIntervalsPer200Pixels * 0.8 : MaximumAxisIntervalsPer200Pixels;
37.409 + // real maximum interval count
37.410 + double maxIntervalCount = availableSize / maxIntervalSize;
37.411 +
37.412 + double range = Math.Abs(ActualMinimum - ActualMaximum);
37.413 + double interval = Math.Pow(10, Exponent(range));
37.414 + double tempInterval = interval;
37.415 +
37.416 + // decrease interval until interval count becomes less than maxIntervalCount
37.417 + while (true)
37.418 + {
37.419 + int mantissa = (int)Mantissa(tempInterval);
37.420 + if (mantissa == 5)
37.421 + {
37.422 + // reduce 5 to 2
37.423 + tempInterval = RemoveNoiseFromDoubleMath(tempInterval / 2.5);
37.424 + }
37.425 + else if (mantissa == 2 || mantissa == 1 || mantissa == 10)
37.426 + {
37.427 + // reduce 2 to 1,10 to 5,1 to 0.5
37.428 + tempInterval = RemoveNoiseFromDoubleMath(tempInterval / 2.0);
37.429 + }
37.430 +
37.431 + if (range / tempInterval > maxIntervalCount)
37.432 + {
37.433 + break;
37.434 + }
37.435 +
37.436 + interval = tempInterval;
37.437 + }
37.438 + return interval;
37.439 + }
37.440 +
37.441 + /// <summary>
37.442 + /// Removes the noise from double math.
37.443 + /// </summary>
37.444 + /// <param name="value">The value.</param>
37.445 + /// <returns>A double without a noise.</returns>
37.446 + internal static double RemoveNoiseFromDoubleMath(double value)
37.447 + {
37.448 + if (value == 0.0 || Math.Abs((Math.Log10(Math.Abs(value)))) < 27)
37.449 + {
37.450 + return (double)((decimal)value);
37.451 + }
37.452 + return Double.Parse(value.ToString(CultureInfo.InvariantCulture), CultureInfo.InvariantCulture);
37.453 + }
37.454 +
37.455 + public void Include(double p)
37.456 + {
37.457 + if (double.IsNaN(p) || double.IsInfinity(p))
37.458 + return;
37.459 +
37.460 + if (double.IsNaN(ActualMinimum))
37.461 + ActualMinimum = p;
37.462 + else
37.463 + ActualMinimum = Math.Min(ActualMinimum, p);
37.464 +
37.465 + if (double.IsNaN(ActualMaximum))
37.466 + ActualMaximum = p;
37.467 + else
37.468 + ActualMaximum = Math.Max(ActualMaximum, p);
37.469 + }
37.470 +
37.471 + }
37.472 +}
37.473 \ No newline at end of file
38.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
38.2 +++ b/External/OxyPlot/OxyPlot/Axes/TickStyle.cs Sat Jun 08 16:53:22 2013 +0000
38.3 @@ -0,0 +1,57 @@
38.4 +// --------------------------------------------------------------------------------------------------------------------
38.5 +// <copyright file="TickStyle.cs" company="OxyPlot">
38.6 +// The MIT License (MIT)
38.7 +//
38.8 +// Copyright (c) 2012 Oystein Bjorke
38.9 +//
38.10 +// Permission is hereby granted, free of charge, to any person obtaining a
38.11 +// copy of this software and associated documentation files (the
38.12 +// "Software"), to deal in the Software without restriction, including
38.13 +// without limitation the rights to use, copy, modify, merge, publish,
38.14 +// distribute, sublicense, and/or sell copies of the Software, and to
38.15 +// permit persons to whom the Software is furnished to do so, subject to
38.16 +// the following conditions:
38.17 +//
38.18 +// The above copyright notice and this permission notice shall be included
38.19 +// in all copies or substantial portions of the Software.
38.20 +//
38.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
38.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
38.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
38.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
38.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
38.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
38.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
38.28 +// </copyright>
38.29 +// <summary>
38.30 +// Tick styles.
38.31 +// </summary>
38.32 +// --------------------------------------------------------------------------------------------------------------------
38.33 +namespace OxyPlot.Axes
38.34 +{
38.35 + /// <summary>
38.36 + /// Specifies the style of axis ticks.
38.37 + /// </summary>
38.38 + public enum TickStyle
38.39 + {
38.40 + /// <summary>
38.41 + /// The ticks are rendered crossing the axis line.
38.42 + /// </summary>
38.43 + Crossing,
38.44 +
38.45 + /// <summary>
38.46 + /// The ticks are rendered inside of the plot area.
38.47 + /// </summary>
38.48 + Inside,
38.49 +
38.50 + /// <summary>
38.51 + /// The ticks are rendered Outside the plot area.
38.52 + /// </summary>
38.53 + Outside,
38.54 +
38.55 + /// <summary>
38.56 + /// The ticks are not rendered.
38.57 + /// </summary>
38.58 + None
38.59 + }
38.60 +}
38.61 \ No newline at end of file
39.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
39.2 +++ b/External/OxyPlot/OxyPlot/Axes/TimeAxis.cs Sat Jun 08 16:53:22 2013 +0000
39.3 @@ -0,0 +1,120 @@
39.4 +// --------------------------------------------------------------------------------------------------------------------
39.5 +// <copyright file="TimeAxis.cs" company="OxyPlot">
39.6 +// The MIT License (MIT)
39.7 +//
39.8 +// Copyright (c) 2012 Oystein Bjorke
39.9 +//
39.10 +// Permission is hereby granted, free of charge, to any person obtaining a
39.11 +// copy of this software and associated documentation files (the
39.12 +// "Software"), to deal in the Software without restriction, including
39.13 +// without limitation the rights to use, copy, modify, merge, publish,
39.14 +// distribute, sublicense, and/or sell copies of the Software, and to
39.15 +// permit persons to whom the Software is furnished to do so, subject to
39.16 +// the following conditions:
39.17 +//
39.18 +// The above copyright notice and this permission notice shall be included
39.19 +// in all copies or substantial portions of the Software.
39.20 +//
39.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
39.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
39.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
39.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
39.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
39.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
39.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
39.28 +// </copyright>
39.29 +// <summary>
39.30 +// Time Axis
39.31 +// The values should be in seconds.
39.32 +// The StringFormat value can be used to force formatting of the axis values
39.33 +// "h:mm" shows hours and minutes
39.34 +// "m:ss" shows minutes and seconds
39.35 +// </summary>
39.36 +// --------------------------------------------------------------------------------------------------------------------
39.37 +using System;
39.38 +using System.Linq;
39.39 +
39.40 +namespace OxyPlot
39.41 +{
39.42 + /// <summary>
39.43 + /// Time Axis
39.44 + /// The values should be in seconds.
39.45 + /// The StringFormat value can be used to force formatting of the axis values
39.46 + /// "h:mm" shows hours and minutes
39.47 + /// "m:ss" shows minutes and seconds
39.48 + /// </summary>
39.49 + public class TimeAxis : LinearAxis
39.50 + {
39.51 + /// <summary>
39.52 + /// Initializes a new instance of the <see cref = "TimeAxis" /> class.
39.53 + /// </summary>
39.54 + /// <param name = "pos">The position.</param>
39.55 + /// <param name = "title">The axis title.</param>
39.56 + /// <param name = "format">The string format for the axis values.</param>
39.57 + public TimeAxis(AxisPosition pos, string title = null, string format = "m:ss")
39.58 + : base(pos, title)
39.59 + {
39.60 + StringFormat = format;
39.61 + }
39.62 +
39.63 + /// <summary>
39.64 + /// Initializes a new instance of the <see cref = "TimeAxis" /> class.
39.65 + /// </summary>
39.66 + /// <param name = "pos">The position.</param>
39.67 + /// <param name = "min">The min.</param>
39.68 + /// <param name = "max">The max.</param>
39.69 + /// <param name = "title">The axis title.</param>
39.70 + /// <param name = "format">The string format for the axis values.</param>
39.71 + public TimeAxis(AxisPosition pos = AxisPosition.Bottom, double min = double.NaN, double max = double.NaN,
39.72 + string title = null, string format = "m:ss")
39.73 + : base(pos, min, max, title)
39.74 + {
39.75 + StringFormat = format;
39.76 + }
39.77 +
39.78 + /// <summary>
39.79 + /// Formats the value.
39.80 + /// </summary>
39.81 + /// <param name = "x">The x.</param>
39.82 + /// <returns></returns>
39.83 + public override string FormatValue(double x)
39.84 + {
39.85 + var span = TimeSpan.FromSeconds(x);
39.86 + string s = ActualStringFormat ?? "h:mm:ss";
39.87 +
39.88 + s = s.Replace("mm", span.Minutes.ToString("00"));
39.89 + s = s.Replace("ss", span.Seconds.ToString("00"));
39.90 + s = s.Replace("hh", span.Hours.ToString("00"));
39.91 + s = s.Replace("msec", span.Milliseconds.ToString("000"));
39.92 + s = s.Replace("m", ((int)span.TotalMinutes).ToString("0"));
39.93 + s = s.Replace("s", ((int)span.TotalSeconds).ToString("0"));
39.94 + s = s.Replace("h", ((int)span.TotalHours).ToString("0"));
39.95 + return s;
39.96 + }
39.97 +
39.98 + protected override double CalculateActualInterval(double availableSize, double maxIntervalSize)
39.99 + {
39.100 + double range = Math.Abs(ActualMinimum - ActualMaximum);
39.101 + double interval = 1;
39.102 + var goodIntervals = new[] { 1.0, 5, 10, 30, 60, 120, 300, 600, 900, 1200, 1800, 3600 };
39.103 +
39.104 + const int maxSteps = 20;
39.105 +
39.106 + while (true)
39.107 + {
39.108 + if (range / interval < maxSteps)
39.109 + {
39.110 + return interval;
39.111 + }
39.112 +
39.113 + double nextInterval = goodIntervals.FirstOrDefault(i => i > interval);
39.114 + if (nextInterval == 0)
39.115 + {
39.116 + nextInterval = interval * 2;
39.117 + }
39.118 +
39.119 + interval = nextInterval;
39.120 + }
39.121 + }
39.122 + }
39.123 +}
39.124 \ No newline at end of file
40.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
40.2 +++ b/External/OxyPlot/OxyPlot/Axes/TimeSpanAxis.cs Sat Jun 08 16:53:22 2013 +0000
40.3 @@ -0,0 +1,197 @@
40.4 +// --------------------------------------------------------------------------------------------------------------------
40.5 +// <copyright file="TimeSpanAxis.cs" company="OxyPlot">
40.6 +// The MIT License (MIT)
40.7 +//
40.8 +// Copyright (c) 2012 Oystein Bjorke
40.9 +//
40.10 +// Permission is hereby granted, free of charge, to any person obtaining a
40.11 +// copy of this software and associated documentation files (the
40.12 +// "Software"), to deal in the Software without restriction, including
40.13 +// without limitation the rights to use, copy, modify, merge, publish,
40.14 +// distribute, sublicense, and/or sell copies of the Software, and to
40.15 +// permit persons to whom the Software is furnished to do so, subject to
40.16 +// the following conditions:
40.17 +//
40.18 +// The above copyright notice and this permission notice shall be included
40.19 +// in all copies or substantial portions of the Software.
40.20 +//
40.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
40.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
40.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
40.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
40.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
40.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
40.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
40.28 +// </copyright>
40.29 +// <summary>
40.30 +// Time axis.
40.31 +// </summary>
40.32 +// --------------------------------------------------------------------------------------------------------------------
40.33 +namespace OxyPlot.Axes
40.34 +{
40.35 + using System;
40.36 + using System.Linq;
40.37 +
40.38 + /// <summary>
40.39 + /// Represents an axis presenting <see cref="System.TimeSpan"/> values.
40.40 + /// </summary>
40.41 + /// <remarks>
40.42 + /// The values should be in seconds.
40.43 + /// The StringFormat value can be used to force formatting of the axis values
40.44 + /// "h:mm" shows hours and minutes
40.45 + /// "m:ss" shows minutes and seconds
40.46 + /// </remarks>
40.47 + public class TimeSpanAxis : LinearAxis
40.48 + {
40.49 + /// <summary>
40.50 + /// Initializes a new instance of the <see cref = "TimeSpanAxis" /> class.
40.51 + /// </summary>
40.52 + public TimeSpanAxis()
40.53 + {
40.54 + }
40.55 +
40.56 + /// <summary>
40.57 + /// Initializes a new instance of the <see cref="TimeSpanAxis"/> class.
40.58 + /// </summary>
40.59 + /// <param name="pos">
40.60 + /// The position.
40.61 + /// </param>
40.62 + /// <param name="title">
40.63 + /// The axis title.
40.64 + /// </param>
40.65 + /// <param name="format">
40.66 + /// The string format for the axis values.
40.67 + /// </param>
40.68 + public TimeSpanAxis(AxisPosition pos, string title = null, string format = "m:ss")
40.69 + : base(pos, title)
40.70 + {
40.71 + this.StringFormat = format;
40.72 + }
40.73 +
40.74 + /// <summary>
40.75 + /// Initializes a new instance of the <see cref="TimeSpanAxis"/> class.
40.76 + /// </summary>
40.77 + /// <param name="pos">
40.78 + /// The position.
40.79 + /// </param>
40.80 + /// <param name="min">
40.81 + /// The min.
40.82 + /// </param>
40.83 + /// <param name="max">
40.84 + /// The max.
40.85 + /// </param>
40.86 + /// <param name="title">
40.87 + /// The axis title.
40.88 + /// </param>
40.89 + /// <param name="format">
40.90 + /// The string format for the axis values.
40.91 + /// </param>
40.92 + public TimeSpanAxis(
40.93 + AxisPosition pos = AxisPosition.Bottom,
40.94 + double min = double.NaN,
40.95 + double max = double.NaN,
40.96 + string title = null,
40.97 + string format = "m:ss")
40.98 + : base(pos, min, max, title)
40.99 + {
40.100 + this.StringFormat = format;
40.101 + }
40.102 +
40.103 + /// <summary>
40.104 + /// Converts a time span to a double.
40.105 + /// </summary>
40.106 + /// <param name="s">
40.107 + /// The time span.
40.108 + /// </param>
40.109 + /// <returns>
40.110 + /// A double value.
40.111 + /// </returns>
40.112 + public static double ToDouble(TimeSpan s)
40.113 + {
40.114 + return s.TotalSeconds;
40.115 + }
40.116 +
40.117 + /// <summary>
40.118 + /// Converts a double to a time span.
40.119 + /// </summary>
40.120 + /// <param name="value">
40.121 + /// The value.
40.122 + /// </param>
40.123 + /// <returns>
40.124 + /// A time span.
40.125 + /// </returns>
40.126 + public static TimeSpan ToTimeSpan(double value)
40.127 + {
40.128 + return TimeSpan.FromSeconds(value);
40.129 + }
40.130 +
40.131 + /// <summary>
40.132 + /// Formats the value.
40.133 + /// </summary>
40.134 + /// <param name="x">
40.135 + /// The x.
40.136 + /// </param>
40.137 + /// <returns>
40.138 + /// The format value.
40.139 + /// </returns>
40.140 + public override string FormatValue(double x)
40.141 + {
40.142 + TimeSpan span = TimeSpan.FromSeconds(x);
40.143 + string s = this.ActualStringFormat ?? "h:mm:ss";
40.144 +
40.145 + s = s.Replace("mm", span.Minutes.ToString("00"));
40.146 + s = s.Replace("ss", span.Seconds.ToString("00"));
40.147 + s = s.Replace("hh", span.Hours.ToString("00"));
40.148 + s = s.Replace("msec", span.Milliseconds.ToString("000"));
40.149 + s = s.Replace("m", ((int)span.TotalMinutes).ToString("0"));
40.150 + s = s.Replace("s", ((int)span.TotalSeconds).ToString("0"));
40.151 + s = s.Replace("h", ((int)span.TotalHours).ToString("0"));
40.152 + return s;
40.153 + }
40.154 +
40.155 + /// <summary>
40.156 + /// Gets the value from an axis coordinate, converts from double to the correct data type if necessary. e.g. DateTimeAxis returns the DateTime and CategoryAxis returns category strings.
40.157 + /// </summary>
40.158 + /// <param name="x">The coordinate.</param>
40.159 + /// <returns>
40.160 + /// The value.
40.161 + /// </returns>
40.162 + public override object GetValue(double x)
40.163 + {
40.164 + return TimeSpan.FromSeconds(x);
40.165 + }
40.166 +
40.167 + /// <summary>
40.168 + /// Calculates the actual interval.
40.169 + /// </summary>
40.170 + /// <param name="availableSize">Size of the available area.</param>
40.171 + /// <param name="maxIntervalSize">Maximum length of the intervals.</param>
40.172 + /// <returns>
40.173 + /// The calculate actual interval.
40.174 + /// </returns>
40.175 + protected override double CalculateActualInterval(double availableSize, double maxIntervalSize)
40.176 + {
40.177 + double range = Math.Abs(this.ActualMinimum - this.ActualMaximum);
40.178 + double interval = 1;
40.179 + var goodIntervals = new[] { 1.0, 5, 10, 30, 60, 120, 300, 600, 900, 1200, 1800, 3600 };
40.180 +
40.181 + int maxNumberOfIntervals = Math.Max((int)(availableSize / maxIntervalSize), 2);
40.182 +
40.183 + while (true)
40.184 + {
40.185 + if (range / interval < maxNumberOfIntervals)
40.186 + {
40.187 + return interval;
40.188 + }
40.189 +
40.190 + double nextInterval = goodIntervals.FirstOrDefault(i => i > interval);
40.191 + if (Math.Abs(nextInterval) < double.Epsilon)
40.192 + {
40.193 + nextInterval = interval * 2;
40.194 + }
40.195 +
40.196 + interval = nextInterval;
40.197 + }
40.198 + }
40.199 + }
40.200 +}
40.201 \ No newline at end of file
41.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
41.2 +++ b/External/OxyPlot/OxyPlot/ClassDiagrams/PlotModel.cd Sat Jun 08 16:53:22 2013 +0000
41.3 @@ -0,0 +1,276 @@
41.4 +<?xml version="1.0" encoding="utf-8"?>
41.5 +<ClassDiagram MajorVersion="1" MinorVersion="1">
41.6 + <Class Name="OxyPlot.PlotModel" Collapsed="true">
41.7 + <Position X="2.5" Y="3.25" Width="2.75" />
41.8 + <Compartments>
41.9 + <Compartment Name="Methods" Collapsed="true" />
41.10 + </Compartments>
41.11 + <TypeIdentifier>
41.12 + <HashCode>EBZwcA2UaBI/BUK9ZBHDJRgBY1uVERMI45sgpP2SPzE=</HashCode>
41.13 + <FileName>PlotModel\PlotModel.cs</FileName>
41.14 + </TypeIdentifier>
41.15 + </Class>
41.16 + <Class Name="OxyPlot.LineSeries" Collapsed="true">
41.17 + <Position X="9.75" Y="7.75" Width="1.5" />
41.18 + <TypeIdentifier>
41.19 + <HashCode>AAQCAAEIAiAAAGCAABBAAAAhRCAMEAAAADAAggACIgA=</HashCode>
41.20 + <FileName>Series\LineSeries.cs</FileName>
41.21 + </TypeIdentifier>
41.22 + </Class>
41.23 + <Class Name="OxyPlot.DataPointSeries" Collapsed="true">
41.24 + <Position X="9.75" Y="6.5" Width="1.5" />
41.25 + <TypeIdentifier>
41.26 + <HashCode>IAAAAAyAEAABgAAAACACAAAABAAEAAAAAAAAAgAAAAA=</HashCode>
41.27 + <FileName>Series\DataPointSeries.cs</FileName>
41.28 + </TypeIdentifier>
41.29 + </Class>
41.30 + <Class Name="OxyPlot.AreaSeries" Collapsed="true">
41.31 + <Position X="11" Y="9" Width="1.5" />
41.32 + <TypeIdentifier>
41.33 + <HashCode>AgAAAAEAEAAAAIAAAAAACAAAAAAECAAAABMAAgIAAAA=</HashCode>
41.34 + <FileName>Series\AreaSeries.cs</FileName>
41.35 + </TypeIdentifier>
41.36 + </Class>
41.37 + <Class Name="OxyPlot.FunctionSeries" Collapsed="true">
41.38 + <Position X="9.25" Y="9" Width="1.5" />
41.39 + <TypeIdentifier>
41.40 + <HashCode>AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=</HashCode>
41.41 + <FileName>Series\FunctionSeries.cs</FileName>
41.42 + </TypeIdentifier>
41.43 + </Class>
41.44 + <Class Name="OxyPlot.LinearAxis" Collapsed="true">
41.45 + <Position X="12" Y="2" Width="1.5" />
41.46 + <TypeIdentifier>
41.47 + <HashCode>AAQAAAAAAQAAACAAAAAAAAAAAAAAAAAAAAEAAAAAQAA=</HashCode>
41.48 + <FileName>Axes\LinearAxis.cs</FileName>
41.49 + </TypeIdentifier>
41.50 + </Class>
41.51 + <Class Name="OxyPlot.LogarithmicAxis" Collapsed="true">
41.52 + <Position X="14.25" Y="2" Width="1.5" />
41.53 + <TypeIdentifier>
41.54 + <HashCode>AAAAAAAAAQAAEgAAAIAAABQAAAAAQAAAAAAAABQAQAA=</HashCode>
41.55 + <FileName>Axes\LogarithmicAxis.cs</FileName>
41.56 + </TypeIdentifier>
41.57 + </Class>
41.58 + <Class Name="OxyPlot.TimeSpanAxis" Collapsed="true">
41.59 + <Position X="12" Y="3.5" Width="1.5" />
41.60 + <TypeIdentifier>
41.61 + <HashCode>AAAAAAAAIAAAAAEAAAAAAAAAAAEAAAAAABEAAAAAAAA=</HashCode>
41.62 + <FileName>Axes\TimeSpanAxis.cs</FileName>
41.63 + </TypeIdentifier>
41.64 + </Class>
41.65 + <Class Name="OxyPlot.CategoryAxis" Collapsed="true">
41.66 + <Position X="14.25" Y="3.5" Width="1.5" />
41.67 + <TypeIdentifier>
41.68 + <HashCode>AIAAEAABMAAEEAgAIBAAAFAAAAAEnAAAAAEgAJAAABE=</HashCode>
41.69 + <FileName>Axes\CategoryAxis.cs</FileName>
41.70 + </TypeIdentifier>
41.71 + </Class>
41.72 + <Class Name="OxyPlot.DateTimeAxis" Collapsed="true">
41.73 + <Position X="16.25" Y="3.5" Width="1.5" />
41.74 + <TypeIdentifier>
41.75 + <HashCode>gAIAAAAAIAAkGAEBAAAAIAAAggAAAAAAABEAAAAVAAA=</HashCode>
41.76 + <FileName>Axes\DateTimeAxis.cs</FileName>
41.77 + </TypeIdentifier>
41.78 + </Class>
41.79 + <Class Name="OxyPlot.Annotation" Collapsed="true">
41.80 + <Position X="25" Y="3.25" Width="1.5" />
41.81 + <TypeIdentifier>
41.82 + <HashCode>gAAQAAAFAAAAAAAAAEAAQAQAAAAAAAAEABAADAACAAA=</HashCode>
41.83 + <FileName>Annotations\Annotation.cs</FileName>
41.84 + </TypeIdentifier>
41.85 + </Class>
41.86 + <Class Name="OxyPlot.LineAnnotation" Collapsed="true">
41.87 + <Position X="25" Y="4.25" Width="1.5" />
41.88 + <TypeIdentifier>
41.89 + <HashCode>BAAQEAAAACBwAIAAABgAgAAAEAAAAAAACTAAkgAgYGA=</HashCode>
41.90 + <FileName>Annotations\LineAnnotation.cs</FileName>
41.91 + </TypeIdentifier>
41.92 + </Class>
41.93 + <Class Name="OxyPlot.BarSeries" Collapsed="true">
41.94 + <Position X="1.5" Y="10.25" Width="1.5" />
41.95 + <TypeIdentifier>
41.96 + <HashCode>CAAAAAgAIAQAAAAAAAAAAAAAAIAAAABAAAAAEAAAAAA=</HashCode>
41.97 + <FileName>Series\BarSeries\BarSeries.cs</FileName>
41.98 + </TypeIdentifier>
41.99 + </Class>
41.100 + <Class Name="OxyPlot.XYAxisSeries" Collapsed="true">
41.101 + <Position X="6.5" Y="5.25" Width="1.5" />
41.102 + <TypeIdentifier>
41.103 + <HashCode>sAAQAAE1WAAAAAAAAEAAQAQAAAAEAAAAABAUACACEAA=</HashCode>
41.104 + <FileName>Series\XYAxisSeries.cs</FileName>
41.105 + </TypeIdentifier>
41.106 + </Class>
41.107 + <Class Name="OxyPlot.CandleStickSeries" Collapsed="true">
41.108 + <Position X="13.5" Y="7.75" Width="1.5" />
41.109 + <TypeIdentifier>
41.110 + <HashCode>AAAAAAEAAAAAAAAAAAAAAAAAAAAAAAAAABAAAAAABAA=</HashCode>
41.111 + <FileName>Series\CandleStickSeries.cs</FileName>
41.112 + </TypeIdentifier>
41.113 + </Class>
41.114 + <Class Name="OxyPlot.HighLowSeries" Collapsed="true">
41.115 + <Position X="13.5" Y="6.5" Width="1.5" />
41.116 + <TypeIdentifier>
41.117 + <HashCode>AAAAAAkBECABCAAAABgAAAQABAQEAAABAHAAggACAAA=</HashCode>
41.118 + <FileName>Series\HighLowSeries.cs</FileName>
41.119 + </TypeIdentifier>
41.120 + </Class>
41.121 + <Class Name="OxyPlot.ItemsSeries" Collapsed="true">
41.122 + <Position X="6.5" Y="4.25" Width="1.5" />
41.123 + <TypeIdentifier>
41.124 + <HashCode>AAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAAAAAAIIAAAA=</HashCode>
41.125 + <FileName>Series\ItemsSeries.cs</FileName>
41.126 + </TypeIdentifier>
41.127 + </Class>
41.128 + <Class Name="OxyPlot.PieSeries" Collapsed="true">
41.129 + <Position X="8.5" Y="4.25" Width="1.5" />
41.130 + <TypeIdentifier>
41.131 + <HashCode>AQAQAAEAWGAYACAIAAAAAAAgAAgEICJAgpQFAoCCAAI=</HashCode>
41.132 + <FileName>Series\PieSeries.cs</FileName>
41.133 + </TypeIdentifier>
41.134 + </Class>
41.135 + <Class Name="OxyPlot.ScatterSeries" Collapsed="true">
41.136 + <Position X="11.75" Y="7.75" Width="1.5" />
41.137 + <TypeIdentifier>
41.138 + <HashCode>AARQAAEIEAAAAEgQAAAIAAAgACBEAAAEABAwAgQDAgA=</HashCode>
41.139 + <FileName>Series\ScatterSeries.cs</FileName>
41.140 + </TypeIdentifier>
41.141 + </Class>
41.142 + <Class Name="OxyPlot.StairStepSeries" Collapsed="true">
41.143 + <Position X="7.5" Y="9" Width="1.5" />
41.144 + <TypeIdentifier>
41.145 + <HashCode>AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAAAgAAAAA=</HashCode>
41.146 + <FileName>Series\StairStepSeries.cs</FileName>
41.147 + </TypeIdentifier>
41.148 + </Class>
41.149 + <Class Name="OxyPlot.StemSeries" Collapsed="true">
41.150 + <Position X="12.75" Y="9" Width="1.5" />
41.151 + <TypeIdentifier>
41.152 + <HashCode>AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAAAgAAQAA=</HashCode>
41.153 + <FileName>Series\StemSeries.cs</FileName>
41.154 + </TypeIdentifier>
41.155 + </Class>
41.156 + <Class Name="OxyPlot.AngleAxis" Collapsed="true">
41.157 + <Position X="18.25" Y="3.5" Width="1.5" />
41.158 + <TypeIdentifier>
41.159 + <HashCode>AAAAAAAAAQAAAAAAAAAAQAQAAAAEAAAAABAAAAAAAAA=</HashCode>
41.160 + <FileName>Axes\AngleAxis.cs</FileName>
41.161 + </TypeIdentifier>
41.162 + </Class>
41.163 + <Class Name="OxyPlot.MagnitudeAxis" Collapsed="true">
41.164 + <Position X="20.25" Y="3.5" Width="1.5" />
41.165 + <TypeIdentifier>
41.166 + <HashCode>AAAAAAAAAQAAAAAAAAAAQAQAAAAEAIAAABAAAAAAAAA=</HashCode>
41.167 + <FileName>Axes\MagnitudeAxis.cs</FileName>
41.168 + </TypeIdentifier>
41.169 + </Class>
41.170 + <Class Name="OxyPlot.Series" Collapsed="true">
41.171 + <Position X="6.5" Y="3.25" Width="1.5" />
41.172 + <TypeIdentifier>
41.173 + <HashCode>AAAQAAEAWABAEEAAAAAAAAAAAAAEAAAAABAkBgISAAA=</HashCode>
41.174 + <FileName>Series\Series.cs</FileName>
41.175 + </TypeIdentifier>
41.176 + <Lollipop Position="0.2" />
41.177 + </Class>
41.178 + <Class Name="OxyPlot.Axis" Collapsed="true">
41.179 + <Position X="13.25" Y="0.5" Width="1.5" />
41.180 + <TypeIdentifier>
41.181 + <HashCode>gEeXCAGRedQgH2V09tJAe5wCkhCEgABEG1cgxZQB4CU=</HashCode>
41.182 + <FileName>Axes\Axis.cs</FileName>
41.183 + </TypeIdentifier>
41.184 + </Class>
41.185 + <Class Name="OxyPlot.ArrowAnnotation" Collapsed="true">
41.186 + <Position X="26.75" Y="4.25" Width="1.5" />
41.187 + <TypeIdentifier>
41.188 + <HashCode>AAQACAAAACBAQAAAQFAAAAAAABAAAAAAgDAAgAAAAAg=</HashCode>
41.189 + <FileName>Annotations\ArrowAnnotation.cs</FileName>
41.190 + </TypeIdentifier>
41.191 + </Class>
41.192 + <Class Name="OxyPlot.PolygonAnnotation" Collapsed="true">
41.193 + <Position X="23.25" Y="4.25" Width="1.5" />
41.194 + <TypeIdentifier>
41.195 + <HashCode>AAAAAAAAACBggAAAABAAAAAAAAAACAAAADAAgAAAAAA=</HashCode>
41.196 + <FileName>Annotations\PolygonAnnotation.cs</FileName>
41.197 + </TypeIdentifier>
41.198 + </Class>
41.199 + <Class Name="OxyPlot.TextAnnotation" Collapsed="true">
41.200 + <Position X="28.5" Y="4.25" Width="1.5" />
41.201 + <TypeIdentifier>
41.202 + <HashCode>AAAAAAAgACBAAIAggAAAAAAAAAgAAAIAABIggAAAgAA=</HashCode>
41.203 + <FileName>Annotations\TextAnnotation.cs</FileName>
41.204 + </TypeIdentifier>
41.205 + </Class>
41.206 + <Class Name="OxyPlot.BarSeriesBase" Collapsed="true">
41.207 + <Position X="2" Y="7.75" Width="1.5" />
41.208 + <TypeIdentifier>
41.209 + <HashCode>BYQAAIEAKCSAACCQAAAAAAABAAgEIBBAAhAUAgoCAAE=</HashCode>
41.210 + <FileName>Series\BarSeries\BarSeriesBase.cs</FileName>
41.211 + </TypeIdentifier>
41.212 + <Lollipop Position="0.2" />
41.213 + </Class>
41.214 + <Class Name="OxyPlot.ColumnSeries" Collapsed="true">
41.215 + <Position X="3.25" Y="10.25" Width="1.5" />
41.216 + <TypeIdentifier>
41.217 + <HashCode>AAAAAAgAIAQAAAAAAEAAAAAAAIAAAABAAAAAEAAAAAA=</HashCode>
41.218 + <FileName>Series\BarSeries\ColumnSeries.cs</FileName>
41.219 + </TypeIdentifier>
41.220 + </Class>
41.221 + <Class Name="OxyPlot.IntervalBarSeries" Collapsed="true">
41.222 + <Position X="3.75" Y="7.75" Width="1.5" />
41.223 + <TypeIdentifier>
41.224 + <HashCode>DQQAAAkBGCSACECAAAAAAAABAIgEIgAAABAUEgoCAAE=</HashCode>
41.225 + <FileName>Series\BarSeries\IntervalBarSeries.cs</FileName>
41.226 + </TypeIdentifier>
41.227 + <Lollipop Position="0.2" />
41.228 + </Class>
41.229 + <Class Name="OxyPlot.RectangleBarSeries" Collapsed="true">
41.230 + <Position X="5.5" Y="6.5" Width="1.75" />
41.231 + <TypeIdentifier>
41.232 + <HashCode>AAAAAAEAECCACACAAAAAAAAAAAgEAAAAABAQAggCAAE=</HashCode>
41.233 + <FileName>Series\BarSeries\RectangleBarSeries.cs</FileName>
41.234 + </TypeIdentifier>
41.235 + </Class>
41.236 + <Class Name="OxyPlot.TornadoBarSeries" Collapsed="true">
41.237 + <Position X="5.5" Y="7.75" Width="1.5" />
41.238 + <TypeIdentifier>
41.239 + <HashCode>DYQAAAsBGCUACEAAAQAgAAABAKgEAoAAABAUEgICAAE=</HashCode>
41.240 + <FileName>Series\BarSeries\TornadoBarSeries.cs</FileName>
41.241 + </TypeIdentifier>
41.242 + </Class>
41.243 + <Class Name="OxyPlot.ColorAxis" Collapsed="true">
41.244 + <Position X="16.25" Y="2" Width="1.5" />
41.245 + <TypeIdentifier>
41.246 + <HashCode>AAAAABAAAQAAAAAAAQIAACAAAAAAAAiAABAAAQAAAAA=</HashCode>
41.247 + <FileName>Axes\ColorAxis.cs</FileName>
41.248 + </TypeIdentifier>
41.249 + </Class>
41.250 + <Class Name="OxyPlot.BarSeriesBase<T>" Collapsed="true">
41.251 + <Position X="2" Y="8.75" Width="1.5" />
41.252 + <TypeIdentifier>
41.253 + <HashCode>AAAAAAAAEAAACEAAAAAAAAAAAAAAAgAAAAAAAAAAAAA=</HashCode>
41.254 + <FileName>Series\BarSeries\BarSeriesBase{T}.cs</FileName>
41.255 + </TypeIdentifier>
41.256 + </Class>
41.257 + <Class Name="OxyPlot.CategorizedSeries" Collapsed="true">
41.258 + <Position X="2" Y="6.5" Width="1.5" />
41.259 + <TypeIdentifier>
41.260 + <HashCode>AAAAAAgAAAAAAAAAAAAAAAAAAIAAAgAAAAAAEAAAAAA=</HashCode>
41.261 + <FileName>Series\BarSeries\CategorizedSeries.cs</FileName>
41.262 + </TypeIdentifier>
41.263 + </Class>
41.264 + <Class Name="OxyPlot.ErrorColumnSeries" Collapsed="true">
41.265 + <Position X="3" Y="11.25" Width="2" />
41.266 + <TypeIdentifier>
41.267 + <HashCode>AAAIAAAAAEAAAAAAAAAAAAAAAAAEABAAAAAAAAAAAAA=</HashCode>
41.268 + <FileName>Series\BarSeries\ErrorColumnSeries.cs</FileName>
41.269 + </TypeIdentifier>
41.270 + </Class>
41.271 + <Interface Name="OxyPlot.ITrackableSeries" Collapsed="true">
41.272 + <Position X="6.5" Y="2" Width="1.5" />
41.273 + <TypeIdentifier>
41.274 + <HashCode>AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAAAgAQAAA=</HashCode>
41.275 + <FileName>Series\ITrackableSeries.cs</FileName>
41.276 + </TypeIdentifier>
41.277 + </Interface>
41.278 + <Font Name="Segoe UI" Size="9" />
41.279 +</ClassDiagram>
41.280 \ No newline at end of file
42.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
42.2 +++ b/External/OxyPlot/OxyPlot/ClassDiagrams/Reporting.cd Sat Jun 08 16:53:22 2013 +0000
42.3 @@ -0,0 +1,204 @@
42.4 +<?xml version="1.0" encoding="utf-8"?>
42.5 +<ClassDiagram MajorVersion="1" MinorVersion="1">
42.6 + <Class Name="OxyPlot.Reporting.TableOfContents" Collapsed="true">
42.7 + <Position X="7.25" Y="12" Width="1.5" />
42.8 + <InheritanceLine Type="OxyPlot.Reporting.ItemsTable" FixedToPoint="true">
42.9 + <Path>
42.10 + <Point X="6.75" Y="11.691" />
42.11 + <Point X="6.75" Y="12.312" />
42.12 + <Point X="7.25" Y="12.312" />
42.13 + </Path>
42.14 + </InheritanceLine>
42.15 + <TypeIdentifier>
42.16 + <HashCode>AAQAAAAAAAAAAAAAAAAAAEAAAAAAAAAAAAAAAABgQAA=</HashCode>
42.17 + <FileName>Reporting\Report\TableOfContents.cs</FileName>
42.18 + </TypeIdentifier>
42.19 + </Class>
42.20 + <Class Name="OxyPlot.Reporting.DrawingFigure" Collapsed="true">
42.21 + <Position X="5.75" Y="8.5" Width="1.5" />
42.22 + <TypeIdentifier>
42.23 + <HashCode>AAAAAAAAAgAAAAAAAAAAAEAAAAgAAAAAAAAAAAAAAAA=</HashCode>
42.24 + <FileName>Reporting\Report\DrawingFigure.cs</FileName>
42.25 + </TypeIdentifier>
42.26 + </Class>
42.27 + <Class Name="OxyPlot.Reporting.Equation" Collapsed="true">
42.28 + <Position X="4.75" Y="5.75" Width="1.5" />
42.29 + <InheritanceLine Type="OxyPlot.Reporting.ReportItem" FixedToPoint="true">
42.30 + <Path>
42.31 + <Point X="3.25" Y="2.312" />
42.32 + <Point X="3.25" Y="6.062" />
42.33 + <Point X="4.75" Y="6.062" />
42.34 + </Path>
42.35 + </InheritanceLine>
42.36 + <TypeIdentifier>
42.37 + <HashCode>AAAAAAAAAgAAAAAAAAAAAEAAAAAAAAAACAAAAAAAAAA=</HashCode>
42.38 + <FileName>Reporting\Report\Equation.cs</FileName>
42.39 + </TypeIdentifier>
42.40 + </Class>
42.41 + <Class Name="OxyPlot.Reporting.Figure" Collapsed="true">
42.42 + <Position X="4.75" Y="7" Width="1.5" />
42.43 + <InheritanceLine Type="OxyPlot.Reporting.ReportItem" FixedToPoint="true">
42.44 + <Path>
42.45 + <Point X="3.25" Y="2.312" />
42.46 + <Point X="3.25" Y="7.312" />
42.47 + <Point X="4.75" Y="7.312" />
42.48 + </Path>
42.49 + </InheritanceLine>
42.50 + <TypeIdentifier>
42.51 + <HashCode>AAAAAAEgAAAIAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=</HashCode>
42.52 + <FileName>Reporting\Report\Figure.cs</FileName>
42.53 + </TypeIdentifier>
42.54 + </Class>
42.55 + <Class Name="OxyPlot.Reporting.Header" Collapsed="true">
42.56 + <Position X="4.75" Y="3.75" Width="1.5" />
42.57 + <InheritanceLine Type="OxyPlot.Reporting.ReportItem" FixedToPoint="true">
42.58 + <Path>
42.59 + <Point X="3.25" Y="2.312" />
42.60 + <Point X="3.25" Y="4.062" />
42.61 + <Point X="4.75" Y="4.062" />
42.62 + </Path>
42.63 + </InheritanceLine>
42.64 + <TypeIdentifier>
42.65 + <HashCode>AAAAAAAAAAAAAAAEAAAAAEAAAAAAAAABAgAACAAAAAA=</HashCode>
42.66 + <FileName>Reporting\Report\Header.cs</FileName>
42.67 + </TypeIdentifier>
42.68 + </Class>
42.69 + <Class Name="OxyPlot.Reporting.Image" Collapsed="true">
42.70 + <Position X="4" Y="8.5" Width="1.5" />
42.71 + <TypeIdentifier>
42.72 + <HashCode>AAAAAAAAAgAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAAAA=</HashCode>
42.73 + <FileName>Reporting\Report\Image.cs</FileName>
42.74 + </TypeIdentifier>
42.75 + </Class>
42.76 + <Class Name="OxyPlot.Reporting.Paragraph" Collapsed="true">
42.77 + <Position X="4.75" Y="4.75" Width="1.5" />
42.78 + <InheritanceLine Type="OxyPlot.Reporting.ReportItem" FixedToPoint="true">
42.79 + <Path>
42.80 + <Point X="3.25" Y="2.312" />
42.81 + <Point X="3.25" Y="5.062" />
42.82 + <Point X="4.75" Y="5.062" />
42.83 + </Path>
42.84 + </InheritanceLine>
42.85 + <TypeIdentifier>
42.86 + <HashCode>AAAAAAAAAAAAAAAAAAAAAEAAAAAAAAAAAAAACAAAAAA=</HashCode>
42.87 + <FileName>Reporting\Report\Paragraph.cs</FileName>
42.88 + </TypeIdentifier>
42.89 + </Class>
42.90 + <Class Name="OxyPlot.Reporting.PlotFigure" Collapsed="true">
42.91 + <Position X="7.5" Y="8.5" Width="1.5" />
42.92 + <TypeIdentifier>
42.93 + <HashCode>AAAAAAAABAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAQAA=</HashCode>
42.94 + <FileName>Reporting\Report\PlotFigure.cs</FileName>
42.95 + </TypeIdentifier>
42.96 + </Class>
42.97 + <Class Name="OxyPlot.Reporting.PropertyTable" Collapsed="true">
42.98 + <Position X="7.25" Y="13" Width="1.5" />
42.99 + <InheritanceLine Type="OxyPlot.Reporting.ItemsTable" FixedToPoint="true">
42.100 + <Path>
42.101 + <Point X="6.75" Y="11.691" />
42.102 + <Point X="6.75" Y="13.312" />
42.103 + <Point X="7.25" Y="13.312" />
42.104 + </Path>
42.105 + </InheritanceLine>
42.106 + <TypeIdentifier>
42.107 + <HashCode>AICAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=</HashCode>
42.108 + <FileName>Reporting\Report\PropertyTable.cs</FileName>
42.109 + </TypeIdentifier>
42.110 + </Class>
42.111 + <Class Name="OxyPlot.Reporting.Report" Collapsed="true">
42.112 + <Position X="4.75" Y="1.75" Width="1.5" />
42.113 + <TypeIdentifier>
42.114 + <HashCode>AAAAAAAAAAAAAEAAgAAAAEAAAAAAAAAAAAAAAAEAAAA=</HashCode>
42.115 + <FileName>Reporting\Report\Report.cs</FileName>
42.116 + </TypeIdentifier>
42.117 + </Class>
42.118 + <Class Name="OxyPlot.Reporting.ReportItem" Collapsed="true">
42.119 + <Position X="2.5" Y="1.75" Width="1.5" />
42.120 + <TypeIdentifier>
42.121 + <HashCode>AAcGAAAAAACCAAAAAAAEAEAAAAAAAAAAAAAAAAELCAA=</HashCode>
42.122 + <FileName>Reporting\Report\ReportItem.cs</FileName>
42.123 + </TypeIdentifier>
42.124 + </Class>
42.125 + <Class Name="OxyPlot.Reporting.ReportSection" Collapsed="true">
42.126 + <Position X="4.75" Y="2.75" Width="1.5" />
42.127 + <InheritanceLine Type="OxyPlot.Reporting.ReportItem" FixedToPoint="true">
42.128 + <Path>
42.129 + <Point X="3.25" Y="2.312" />
42.130 + <Point X="3.25" Y="3.062" />
42.131 + <Point X="4.75" Y="3.062" />
42.132 + </Path>
42.133 + </InheritanceLine>
42.134 + <TypeIdentifier>
42.135 + <HashCode>AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=</HashCode>
42.136 + <FileName>Reporting\Report\ReportSection.cs</FileName>
42.137 + </TypeIdentifier>
42.138 + </Class>
42.139 + <Class Name="OxyPlot.Reporting.Table" Collapsed="true">
42.140 + <Position X="4.75" Y="10" Width="1.5" />
42.141 + <InheritanceLine Type="OxyPlot.Reporting.ReportItem" FixedToPoint="true">
42.142 + <Path>
42.143 + <Point X="3.25" Y="2.312" />
42.144 + <Point X="3.25" Y="10.312" />
42.145 + <Point X="4.75" Y="10.312" />
42.146 + </Path>
42.147 + </InheritanceLine>
42.148 + <TypeIdentifier>
42.149 + <HashCode>AAQAAAAgAAAAAEAgAAAAAEBAAAAAAAEACAAAAAgAAAA=</HashCode>
42.150 + <FileName>Reporting\Report\Table.cs</FileName>
42.151 + </TypeIdentifier>
42.152 + </Class>
42.153 + <Class Name="OxyPlot.Reporting.HtmlReportWriter" Collapsed="true" BaseTypeListCollapsed="true">
42.154 + <Position X="7.75" Y="2.75" Width="1.5" />
42.155 + <TypeIdentifier>
42.156 + <HashCode>ACAAgAAAAAAgAIQAAAAQAAAAAAoUAABAIEIkAAigAAA=</HashCode>
42.157 + <FileName>Reporting\ReportWriters\HtmlReportWriter.cs</FileName>
42.158 + </TypeIdentifier>
42.159 + <Lollipop Position="0.2" />
42.160 + </Class>
42.161 + <Class Name="OxyPlot.Reporting.LatexReportWriter" Collapsed="true" BaseTypeListCollapsed="true">
42.162 + <Position X="11.25" Y="2.75" Width="1.5" />
42.163 + <TypeIdentifier>
42.164 + <HashCode>ACABgAAAACAsAAQABAAAAAQAAAAAIAAAAEAkAAAiAAA=</HashCode>
42.165 + <FileName>Reporting\ReportWriters\LatexReportWriter.cs</FileName>
42.166 + </TypeIdentifier>
42.167 + <Lollipop Position="0.2" />
42.168 + </Class>
42.169 + <Class Name="OxyPlot.Reporting.TextReportWriter" Collapsed="true" BaseTypeListCollapsed="true">
42.170 + <Position X="9.5" Y="2.75" Width="1.5" />
42.171 + <TypeIdentifier>
42.172 + <HashCode>ICAAgABAAAAgAAQIAAAACIAEAAAAAAAAAEAkAAAgAAA=</HashCode>
42.173 + <FileName>Reporting\ReportWriters\TextReportWriter.cs</FileName>
42.174 + </TypeIdentifier>
42.175 + <Lollipop Position="0.2" />
42.176 + </Class>
42.177 + <Class Name="OxyPlot.Reporting.ItemsTable" Collapsed="true">
42.178 + <Position X="6" Y="11" Width="1.5" />
42.179 + <InheritanceLine Type="OxyPlot.Reporting.Table" FixedToPoint="true">
42.180 + <Path>
42.181 + <Point X="5.5" Y="10.691" />
42.182 + <Point X="5.5" Y="11.312" />
42.183 + <Point X="6" Y="11.312" />
42.184 + </Path>
42.185 + </InheritanceLine>
42.186 + <TypeIdentifier>
42.187 + <HashCode>AAAAAgAAIAAACAAAACgIAEAAAAAAAAAAAAAAAAhAgAA=</HashCode>
42.188 + <FileName>Reporting\Report\ItemsTable.cs</FileName>
42.189 + </TypeIdentifier>
42.190 + </Class>
42.191 + <Class Name="OxyPlot.Reporting.WikiReportWriter" Collapsed="true">
42.192 + <Position X="13" Y="2.75" Width="1.5" />
42.193 + <TypeIdentifier>
42.194 + <HashCode>ICAAkABAAAAgAAQIAAAACIAEAAAAAACEAEAkAAAgAAA=</HashCode>
42.195 + <FileName>Reporting\ReportWriters\WikiReportWriter.cs</FileName>
42.196 + </TypeIdentifier>
42.197 + <Lollipop Position="0.2" />
42.198 + </Class>
42.199 + <Interface Name="OxyPlot.Reporting.IReportWriter" Collapsed="true">
42.200 + <Position X="9.5" Y="1.75" Width="1.5" />
42.201 + <TypeIdentifier>
42.202 + <HashCode>ACAAgAAAAAAgAAQAAAAAAAAAAAAAAAAAAEAkAAAgAAA=</HashCode>
42.203 + <FileName>Reporting\ReportWriters\IReportWriter.cs</FileName>
42.204 + </TypeIdentifier>
42.205 + </Interface>
42.206 + <Font Name="Segoe UI" Size="9" />
42.207 +</ClassDiagram>
42.208 \ No newline at end of file
43.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
43.2 +++ b/External/OxyPlot/OxyPlot/ClassDiagrams/Series.cd Sat Jun 08 16:53:22 2013 +0000
43.3 @@ -0,0 +1,161 @@
43.4 +<?xml version="1.0" encoding="utf-8"?>
43.5 +<ClassDiagram MajorVersion="1" MinorVersion="1">
43.6 + <Class Name="OxyPlot.LineSeries" Collapsed="true">
43.7 + <Position X="6.75" Y="5" Width="1.5" />
43.8 + <TypeIdentifier>
43.9 + <HashCode>AAQCAAEIAiAAAGCAABBAAAAhRCAMEAAAADAAggAKIgA=</HashCode>
43.10 + <FileName>Series\LineSeries.cs</FileName>
43.11 + </TypeIdentifier>
43.12 + </Class>
43.13 + <Class Name="OxyPlot.DataPointSeries" Collapsed="true">
43.14 + <Position X="6.75" Y="3.75" Width="1.5" />
43.15 + <TypeIdentifier>
43.16 + <HashCode>IAAAAAyAEAABgAAAACACAAAABAAEAAAAAAAAAgAAAAA=</HashCode>
43.17 + <FileName>Series\DataPointSeries.cs</FileName>
43.18 + </TypeIdentifier>
43.19 + </Class>
43.20 + <Class Name="OxyPlot.AreaSeries" Collapsed="true">
43.21 + <Position X="8.75" Y="6.25" Width="1.5" />
43.22 + <TypeIdentifier>
43.23 + <HashCode>AgAAAAEAEAAAAIAAAAAACAAAAAAECAAAABMAAgIAAAA=</HashCode>
43.24 + <FileName>Series\AreaSeries.cs</FileName>
43.25 + </TypeIdentifier>
43.26 + </Class>
43.27 + <Class Name="OxyPlot.FunctionSeries" Collapsed="true">
43.28 + <Position X="7" Y="6.25" Width="1.5" />
43.29 + <TypeIdentifier>
43.30 + <HashCode>AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=</HashCode>
43.31 + <FileName>Series\FunctionSeries.cs</FileName>
43.32 + </TypeIdentifier>
43.33 + </Class>
43.34 + <Class Name="OxyPlot.BarSeries" Collapsed="true">
43.35 + <Position X="0.5" Y="7.25" Width="1.5" />
43.36 + <TypeIdentifier>
43.37 + <HashCode>CAAAAAgAIAQAAAAAAAAAAAAAAIAAAABAAAAAEAAAAAA=</HashCode>
43.38 + <FileName>Series\BarSeries\BarSeries.cs</FileName>
43.39 + </TypeIdentifier>
43.40 + </Class>
43.41 + <Class Name="OxyPlot.XYAxisSeries" Collapsed="true">
43.42 + <Position X="5.5" Y="2.5" Width="1.5" />
43.43 + <TypeIdentifier>
43.44 + <HashCode>sAAQAAE1WAAAAAAAAEAAQAQAAAAEAAAAABAUACACEAA=</HashCode>
43.45 + <FileName>Series\XYAxisSeries.cs</FileName>
43.46 + </TypeIdentifier>
43.47 + </Class>
43.48 + <Class Name="OxyPlot.CandleStickSeries" Collapsed="true">
43.49 + <Position X="10.5" Y="5" Width="1.5" />
43.50 + <TypeIdentifier>
43.51 + <HashCode>AAAAAAEAAAAAAAAAAAAAAAAAAAAAAAAAABAAAAAABAA=</HashCode>
43.52 + <FileName>Series\CandleStickSeries.cs</FileName>
43.53 + </TypeIdentifier>
43.54 + </Class>
43.55 + <Class Name="OxyPlot.HighLowSeries" Collapsed="true">
43.56 + <Position X="10.5" Y="3.75" Width="1.5" />
43.57 + <TypeIdentifier>
43.58 + <HashCode>AAAAAAkBECABCAAAABgAAAQABAQEAAABAHAAggAKAAA=</HashCode>
43.59 + <FileName>Series\HighLowSeries.cs</FileName>
43.60 + </TypeIdentifier>
43.61 + </Class>
43.62 + <Class Name="OxyPlot.ItemsSeries" Collapsed="true">
43.63 + <Position X="5.5" Y="1.5" Width="1.5" />
43.64 + <TypeIdentifier>
43.65 + <HashCode>AAAAAAAAAAAAAEAAAAAAAAAAAAAAAAAAAAAAAIIAAAA=</HashCode>
43.66 + <FileName>Series\ItemsSeries.cs</FileName>
43.67 + </TypeIdentifier>
43.68 + </Class>
43.69 + <Class Name="OxyPlot.PieSeries" Collapsed="true">
43.70 + <Position X="7.5" Y="1.5" Width="1.5" />
43.71 + <TypeIdentifier>
43.72 + <HashCode>AQAQAAEAWGAYACAIAAAAAAAgAAgEICJAgpQFAoCCAAI=</HashCode>
43.73 + <FileName>Series\PieSeries.cs</FileName>
43.74 + </TypeIdentifier>
43.75 + </Class>
43.76 + <Class Name="OxyPlot.ScatterSeries" Collapsed="true">
43.77 + <Position X="8.75" Y="5" Width="1.5" />
43.78 + <TypeIdentifier>
43.79 + <HashCode>AARQAAEIEAAAAEgQAAAIAAAgACBEQAIEABAwAgQDAgA=</HashCode>
43.80 + <FileName>Series\ScatterSeries.cs</FileName>
43.81 + </TypeIdentifier>
43.82 + </Class>
43.83 + <Class Name="OxyPlot.StairStepSeries" Collapsed="true">
43.84 + <Position X="5.25" Y="6.25" Width="1.5" />
43.85 + <TypeIdentifier>
43.86 + <HashCode>AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAAAgAAAAA=</HashCode>
43.87 + <FileName>Series\StairStepSeries.cs</FileName>
43.88 + </TypeIdentifier>
43.89 + </Class>
43.90 + <Class Name="OxyPlot.StemSeries" Collapsed="true">
43.91 + <Position X="10.5" Y="6.25" Width="1.5" />
43.92 + <TypeIdentifier>
43.93 + <HashCode>AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAAAgAAQAA=</HashCode>
43.94 + <FileName>Series\StemSeries.cs</FileName>
43.95 + </TypeIdentifier>
43.96 + </Class>
43.97 + <Class Name="OxyPlot.Series" Collapsed="true">
43.98 + <Position X="5.5" Y="0.5" Width="1.5" />
43.99 + <TypeIdentifier>
43.100 + <HashCode>AAAQAAEAWABAEEAAAAAAAAAAAAAEAAAAABAkBgISAAA=</HashCode>
43.101 + <FileName>Series\Series.cs</FileName>
43.102 + </TypeIdentifier>
43.103 + <Lollipop Position="0.2" />
43.104 + </Class>
43.105 + <Class Name="OxyPlot.BarSeriesBase" Collapsed="true">
43.106 + <Position X="1" Y="5" Width="1.5" />
43.107 + <TypeIdentifier>
43.108 + <HashCode>BYQAgIEAKCSAACCQAAAAAAABAAgEIBBAAhAUEgoCAAE=</HashCode>
43.109 + <FileName>Series\BarSeries\BarSeriesBase.cs</FileName>
43.110 + </TypeIdentifier>
43.111 + <Lollipop Position="0.2" />
43.112 + </Class>
43.113 + <Class Name="OxyPlot.ColumnSeries" Collapsed="true">
43.114 + <Position X="2.25" Y="7.25" Width="1.5" />
43.115 + <TypeIdentifier>
43.116 + <HashCode>AAAAAAgAIAQAAAAAAEAAAAAAAIAAAABAAAAAEAAAAAA=</HashCode>
43.117 + <FileName>Series\BarSeries\ColumnSeries.cs</FileName>
43.118 + </TypeIdentifier>
43.119 + </Class>
43.120 + <Class Name="OxyPlot.IntervalBarSeries" Collapsed="true">
43.121 + <Position X="2.75" Y="5" Width="1.5" />
43.122 + <TypeIdentifier>
43.123 + <HashCode>DQQAgAkBGCSACECAAAAAAAABAIgEIgAAABAUEgoCAAE=</HashCode>
43.124 + <FileName>Series\BarSeries\IntervalBarSeries.cs</FileName>
43.125 + </TypeIdentifier>
43.126 + <Lollipop Position="0.2" />
43.127 + </Class>
43.128 + <Class Name="OxyPlot.RectangleBarSeries" Collapsed="true">
43.129 + <Position X="4.5" Y="3.75" Width="1.75" />
43.130 + <TypeIdentifier>
43.131 + <HashCode>AAAAgAEAECCACACAAAAAAAAAAAgEAAAAABAQEggCAAE=</HashCode>
43.132 + <FileName>Series\BarSeries\RectangleBarSeries.cs</FileName>
43.133 + </TypeIdentifier>
43.134 + </Class>
43.135 + <Class Name="OxyPlot.TornadoBarSeries" Collapsed="true">
43.136 + <Position X="4.5" Y="5" Width="1.5" />
43.137 + <TypeIdentifier>
43.138 + <HashCode>DYQAAAsBGCUICEAABQAgAAAFAKgEAoAAABA0EgICAAE=</HashCode>
43.139 + <FileName>Series\BarSeries\TornadoBarSeries.cs</FileName>
43.140 + </TypeIdentifier>
43.141 + </Class>
43.142 + <Class Name="OxyPlot.BarSeriesBase<T>" Collapsed="true">
43.143 + <Position X="1" Y="6" Width="1.5" />
43.144 + <TypeIdentifier>
43.145 + <HashCode>AAAAAAAAEAAACEAAAAAAAAAAAAAAAgAAAAAAAAAAAAA=</HashCode>
43.146 + <FileName>Series\BarSeries\BarSeriesBase{T}.cs</FileName>
43.147 + </TypeIdentifier>
43.148 + </Class>
43.149 + <Class Name="OxyPlot.CategorizedSeries" Collapsed="true">
43.150 + <Position X="1" Y="3.75" Width="1.5" />
43.151 + <TypeIdentifier>
43.152 + <HashCode>AAAAAAgAAAAAAAAAAAAAAAAAAIAAAgAAAAAAEAAAAAA=</HashCode>
43.153 + <FileName>Series\BarSeries\CategorizedSeries.cs</FileName>
43.154 + </TypeIdentifier>
43.155 + </Class>
43.156 + <Class Name="OxyPlot.ErrorColumnSeries" Collapsed="true">
43.157 + <Position X="2" Y="8.25" Width="2" />
43.158 + <TypeIdentifier>
43.159 + <HashCode>AAAIAAAAAEAAAAAAAAAAAAAAAAAEABAAAAAAAAAAAAA=</HashCode>
43.160 + <FileName>Series\BarSeries\ErrorColumnSeries.cs</FileName>
43.161 + </TypeIdentifier>
43.162 + </Class>
43.163 + <Font Name="Segoe UI" Size="9" />
43.164 +</ClassDiagram>
43.165 \ No newline at end of file
44.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
44.2 +++ b/External/OxyPlot/OxyPlot/Foundation/ArrayHelper.cs Sat Jun 08 16:53:22 2013 +0000
44.3 @@ -0,0 +1,124 @@
44.4 +// --------------------------------------------------------------------------------------------------------------------
44.5 +// <copyright file="ArrayHelper.cs" company="OxyPlot">
44.6 +// The MIT License (MIT)
44.7 +//
44.8 +// Copyright (c) 2012 Oystein Bjorke
44.9 +//
44.10 +// Permission is hereby granted, free of charge, to any person obtaining a
44.11 +// copy of this software and associated documentation files (the
44.12 +// "Software"), to deal in the Software without restriction, including
44.13 +// without limitation the rights to use, copy, modify, merge, publish,
44.14 +// distribute, sublicense, and/or sell copies of the Software, and to
44.15 +// permit persons to whom the Software is furnished to do so, subject to
44.16 +// the following conditions:
44.17 +//
44.18 +// The above copyright notice and this permission notice shall be included
44.19 +// in all copies or substantial portions of the Software.
44.20 +//
44.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
44.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
44.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
44.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
44.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
44.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
44.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
44.28 +// </copyright>
44.29 +// <summary>
44.30 +// Array helper methods.
44.31 +// </summary>
44.32 +// --------------------------------------------------------------------------------------------------------------------
44.33 +namespace OxyPlot
44.34 +{
44.35 + using System;
44.36 +
44.37 + /// <summary>
44.38 + /// Provides utility methods for vector generation.
44.39 + /// </summary>
44.40 + public static class ArrayHelper
44.41 + {
44.42 + /// <summary>
44.43 + /// Creates a vector.
44.44 + /// </summary>
44.45 + /// <param name="x0">
44.46 + /// The first value.
44.47 + /// </param>
44.48 + /// <param name="x1">
44.49 + /// The last value.
44.50 + /// </param>
44.51 + /// <param name="n">
44.52 + /// The number of steps.
44.53 + /// </param>
44.54 + /// <returns>
44.55 + /// A vector.
44.56 + /// </returns>
44.57 + public static double[] CreateVector(double x0, double x1, int n)
44.58 + {
44.59 + var result = new double[n];
44.60 + for (int i = 0; i < n; i++)
44.61 + {
44.62 + result[i] = (x0 + ((x1 - x0) * i / (n - 1))).RemoveNoise();
44.63 + }
44.64 +
44.65 + return result;
44.66 + }
44.67 +
44.68 + /// <summary>
44.69 + /// Creates a vector.
44.70 + /// </summary>
44.71 + /// <param name="x0">
44.72 + /// The first value.
44.73 + /// </param>
44.74 + /// <param name="x1">
44.75 + /// The last value.
44.76 + /// </param>
44.77 + /// <param name="dx">
44.78 + /// The step size.
44.79 + /// </param>
44.80 + /// <returns>
44.81 + /// A vector.
44.82 + /// </returns>
44.83 + public static double[] CreateVector(double x0, double x1, double dx)
44.84 + {
44.85 + var n = (int)Math.Round((x1 - x0) / dx);
44.86 + var result = new double[n + 1];
44.87 + for (int i = 0; i <= n; i++)
44.88 + {
44.89 + result[i] = (x0 + (i * dx)).RemoveNoise();
44.90 + }
44.91 +
44.92 + return result;
44.93 + }
44.94 +
44.95 + /// <summary>
44.96 + /// Evaluates the specified function.
44.97 + /// </summary>
44.98 + /// <param name="f">
44.99 + /// The function.
44.100 + /// </param>
44.101 + /// <param name="x">
44.102 + /// The x values.
44.103 + /// </param>
44.104 + /// <param name="y">
44.105 + /// The y values.
44.106 + /// </param>
44.107 + /// <returns>
44.108 + /// Array of evaluations. The value of f(x_i,y_j) will be placed at index [i, j].
44.109 + /// </returns>
44.110 + public static double[,] Evaluate(Func<double, double, double> f, double[] x, double[] y)
44.111 + {
44.112 + int m = x.Length;
44.113 + int n = y.Length;
44.114 + var result = new double[m, n];
44.115 + for (int i = 0; i < m; i++)
44.116 + {
44.117 + for (int j = 0; j < n; j++)
44.118 + {
44.119 + result[i, j] = f(x[i], y[j]);
44.120 + }
44.121 + }
44.122 +
44.123 + return result;
44.124 + }
44.125 +
44.126 + }
44.127 +}
44.128 \ No newline at end of file
45.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
45.2 +++ b/External/OxyPlot/OxyPlot/Foundation/CanonicalSplineHelper.cs Sat Jun 08 16:53:22 2013 +0000
45.3 @@ -0,0 +1,252 @@
45.4 +// --------------------------------------------------------------------------------------------------------------------
45.5 +// <copyright file="CanonicalSplineHelper.cs" company="OxyPlot">
45.6 +// The MIT License (MIT)
45.7 +//
45.8 +// Copyright (c) 2012 Oystein Bjorke
45.9 +//
45.10 +// Permission is hereby granted, free of charge, to any person obtaining a
45.11 +// copy of this software and associated documentation files (the
45.12 +// "Software"), to deal in the Software without restriction, including
45.13 +// without limitation the rights to use, copy, modify, merge, publish,
45.14 +// distribute, sublicense, and/or sell copies of the Software, and to
45.15 +// permit persons to whom the Software is furnished to do so, subject to
45.16 +// the following conditions:
45.17 +//
45.18 +// The above copyright notice and this permission notice shall be included
45.19 +// in all copies or substantial portions of the Software.
45.20 +//
45.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
45.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
45.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
45.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
45.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
45.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
45.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
45.28 +// </copyright>
45.29 +// <summary>
45.30 +// Interpolates a list of points using a canonical spline.
45.31 +// </summary>
45.32 +// --------------------------------------------------------------------------------------------------------------------
45.33 +namespace OxyPlot
45.34 +{
45.35 + using System;
45.36 + using System.Collections.Generic;
45.37 + using System.Linq;
45.38 +
45.39 + /// <summary>
45.40 + /// Provides functionality to interpolate a list of points by a canonical spline.
45.41 + /// </summary>
45.42 + internal static class CanonicalSplineHelper
45.43 + {
45.44 + // CanonicalSplineHelper.cs (c) 2009 by Charles Petzold (WPF and Silverlight)
45.45 + // www.charlespetzold.com/blog/2009/01/Canonical-Splines-in-WPF-and-Silverlight.html
45.46 + /// <summary>
45.47 + /// Creates a spline of data points.
45.48 + /// </summary>
45.49 + /// <param name="points">
45.50 + /// The points.
45.51 + /// </param>
45.52 + /// <param name="tension">
45.53 + /// The tension.
45.54 + /// </param>
45.55 + /// <param name="tensions">
45.56 + /// The tensions.
45.57 + /// </param>
45.58 + /// <param name="isClosed">
45.59 + /// True if the spline is closed.
45.60 + /// </param>
45.61 + /// <param name="tolerance">
45.62 + /// The tolerance.
45.63 + /// </param>
45.64 + /// <returns>
45.65 + /// A list of data points.
45.66 + /// </returns>
45.67 + internal static List<IDataPoint> CreateSpline(
45.68 + IList<IDataPoint> points, double tension, IList<double> tensions, bool isClosed, double tolerance)
45.69 + {
45.70 + var screenPoints = points.Select(p => new ScreenPoint(p.X, p.Y)).ToList();
45.71 + var interpolatedScreenPoints = CreateSpline(screenPoints, tension, tensions, isClosed, tolerance);
45.72 + var interpolatedDataPoints = new List<IDataPoint>(interpolatedScreenPoints.Count);
45.73 +
45.74 + foreach (var s in interpolatedScreenPoints)
45.75 + {
45.76 + interpolatedDataPoints.Add(new DataPoint(s.X, s.Y));
45.77 + }
45.78 +
45.79 + return interpolatedDataPoints;
45.80 + }
45.81 +
45.82 + /// <summary>
45.83 + /// Creates a spline of screen points.
45.84 + /// </summary>
45.85 + /// <param name="points">
45.86 + /// The points.
45.87 + /// </param>
45.88 + /// <param name="tension">
45.89 + /// The tension.
45.90 + /// </param>
45.91 + /// <param name="tensions">
45.92 + /// The tensions.
45.93 + /// </param>
45.94 + /// <param name="isClosed">
45.95 + /// True if the spline is closed.
45.96 + /// </param>
45.97 + /// <param name="tolerance">
45.98 + /// The tolerance.
45.99 + /// </param>
45.100 + /// <returns>
45.101 + /// A list of screen points.
45.102 + /// </returns>
45.103 + internal static List<ScreenPoint> CreateSpline(
45.104 + IList<ScreenPoint> points, double tension, IList<double> tensions, bool isClosed, double tolerance)
45.105 + {
45.106 + var result = new List<ScreenPoint>();
45.107 + if (points == null)
45.108 + {
45.109 + return result;
45.110 + }
45.111 +
45.112 + int n = points.Count;
45.113 + if (n < 1)
45.114 + {
45.115 + return result;
45.116 + }
45.117 +
45.118 + if (n < 2)
45.119 + {
45.120 + result.AddRange(points);
45.121 + return result;
45.122 + }
45.123 +
45.124 + if (n == 2)
45.125 + {
45.126 + if (!isClosed)
45.127 + {
45.128 + Segment(result, points[0], points[0], points[1], points[1], tension, tension, tolerance);
45.129 + }
45.130 + else
45.131 + {
45.132 + Segment(result, points[1], points[0], points[1], points[0], tension, tension, tolerance);
45.133 + Segment(result, points[0], points[1], points[0], points[1], tension, tension, tolerance);
45.134 + }
45.135 + }
45.136 + else
45.137 + {
45.138 + bool useTensionCollection = tensions != null && tensions.Count > 0;
45.139 +
45.140 + for (int i = 0; i < n; i++)
45.141 + {
45.142 + double t1 = useTensionCollection ? tensions[i % tensions.Count] : tension;
45.143 + double t2 = useTensionCollection ? tensions[(i + 1) % tensions.Count] : tension;
45.144 +
45.145 + if (i == 0)
45.146 + {
45.147 + Segment(
45.148 + result,
45.149 + isClosed ? points[n - 1] : points[0],
45.150 + points[0],
45.151 + points[1],
45.152 + points[2],
45.153 + t1,
45.154 + t2,
45.155 + tolerance);
45.156 + }
45.157 + else if (i == n - 2)
45.158 + {
45.159 + Segment(
45.160 + result,
45.161 + points[i - 1],
45.162 + points[i],
45.163 + points[i + 1],
45.164 + isClosed ? points[0] : points[i + 1],
45.165 + t1,
45.166 + t2,
45.167 + tolerance);
45.168 + }
45.169 + else if (i == n - 1)
45.170 + {
45.171 + if (isClosed)
45.172 + {
45.173 + Segment(result, points[i - 1], points[i], points[0], points[1], t1, t2, tolerance);
45.174 + }
45.175 + }
45.176 + else
45.177 + {
45.178 + Segment(result, points[i - 1], points[i], points[i + 1], points[i + 2], t1, t2, tolerance);
45.179 + }
45.180 + }
45.181 + }
45.182 +
45.183 + return result;
45.184 + }
45.185 +
45.186 + /// <summary>
45.187 + /// The segment.
45.188 + /// </summary>
45.189 + /// <param name="points">
45.190 + /// The points.
45.191 + /// </param>
45.192 + /// <param name="pt0">
45.193 + /// The pt 0.
45.194 + /// </param>
45.195 + /// <param name="pt1">
45.196 + /// The pt 1.
45.197 + /// </param>
45.198 + /// <param name="pt2">
45.199 + /// The pt 2.
45.200 + /// </param>
45.201 + /// <param name="pt3">
45.202 + /// The pt 3.
45.203 + /// </param>
45.204 + /// <param name="t1">
45.205 + /// The t 1.
45.206 + /// </param>
45.207 + /// <param name="t2">
45.208 + /// The t 2.
45.209 + /// </param>
45.210 + /// <param name="tolerance">
45.211 + /// The tolerance.
45.212 + /// </param>
45.213 + private static void Segment(
45.214 + IList<ScreenPoint> points,
45.215 + ScreenPoint pt0,
45.216 + ScreenPoint pt1,
45.217 + ScreenPoint pt2,
45.218 + ScreenPoint pt3,
45.219 + double t1,
45.220 + double t2,
45.221 + double tolerance)
45.222 + {
45.223 + // See Petzold, "Programming Microsoft Windows with C#", pages 645-646 or
45.224 + // Petzold, "Programming Microsoft Windows with Microsoft Visual Basic .NET", pages 638-639
45.225 + // for derivation of the following formulas:
45.226 + double sx1 = t1 * (pt2.X - pt0.X);
45.227 + double sy1 = t1 * (pt2.Y - pt0.Y);
45.228 + double sx2 = t2 * (pt3.X - pt1.X);
45.229 + double sy2 = t2 * (pt3.Y - pt1.Y);
45.230 +
45.231 + double ax = sx1 + sx2 + 2 * pt1.X - 2 * pt2.X;
45.232 + double ay = sy1 + sy2 + 2 * pt1.Y - 2 * pt2.Y;
45.233 + double bx = -2 * sx1 - sx2 - 3 * pt1.X + 3 * pt2.X;
45.234 + double by = -2 * sy1 - sy2 - 3 * pt1.Y + 3 * pt2.Y;
45.235 +
45.236 + double cx = sx1;
45.237 + double cy = sy1;
45.238 + double dx = pt1.X;
45.239 + double dy = pt1.Y;
45.240 +
45.241 + var num = (int)((Math.Abs(pt1.X - pt2.X) + Math.Abs(pt1.Y - pt2.Y)) / tolerance);
45.242 +
45.243 + // Notice begins at 1 so excludes the first point (which is just pt1)
45.244 + for (int i = 1; i < num; i++)
45.245 + {
45.246 + double t = (double)i / (num - 1);
45.247 + var pt = new ScreenPoint(
45.248 + ax * t * t * t + bx * t * t + cx * t + dx,
45.249 + ay * t * t * t + by * t * t + cy * t + dy);
45.250 + points.Add(pt);
45.251 + }
45.252 + }
45.253 +
45.254 + }
45.255 +}
45.256 \ No newline at end of file
46.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
46.2 +++ b/External/OxyPlot/OxyPlot/Foundation/CodeGenerator/CodeGenerationAttribute.cs Sat Jun 08 16:53:22 2013 +0000
46.3 @@ -0,0 +1,57 @@
46.4 +// --------------------------------------------------------------------------------------------------------------------
46.5 +// <copyright file="CodeGenerationAttribute.cs" company="OxyPlot">
46.6 +// The MIT License (MIT)
46.7 +//
46.8 +// Copyright (c) 2012 Oystein Bjorke
46.9 +//
46.10 +// Permission is hereby granted, free of charge, to any person obtaining a
46.11 +// copy of this software and associated documentation files (the
46.12 +// "Software"), to deal in the Software without restriction, including
46.13 +// without limitation the rights to use, copy, modify, merge, publish,
46.14 +// distribute, sublicense, and/or sell copies of the Software, and to
46.15 +// permit persons to whom the Software is furnished to do so, subject to
46.16 +// the following conditions:
46.17 +//
46.18 +// The above copyright notice and this permission notice shall be included
46.19 +// in all copies or substantial portions of the Software.
46.20 +//
46.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
46.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
46.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
46.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
46.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
46.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
46.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
46.28 +// </copyright>
46.29 +// <summary>
46.30 +// Attribute that controls if code should be generated for the property.
46.31 +// </summary>
46.32 +// --------------------------------------------------------------------------------------------------------------------
46.33 +namespace OxyPlot
46.34 +{
46.35 + using System;
46.36 +
46.37 + /// <summary>
46.38 + /// Specifies whether code should be generated for the property.
46.39 + /// </summary>
46.40 + [AttributeUsage(AttributeTargets.Property)]
46.41 + public class CodeGenerationAttribute : Attribute
46.42 + {
46.43 + /// <summary>
46.44 + /// Initializes a new instance of the <see cref="CodeGenerationAttribute"/> class.
46.45 + /// </summary>
46.46 + /// <param name="generateCode">
46.47 + /// The generate code.
46.48 + /// </param>
46.49 + public CodeGenerationAttribute(bool generateCode)
46.50 + {
46.51 + this.GenerateCode = generateCode;
46.52 + }
46.53 +
46.54 + /// <summary>
46.55 + /// Gets or sets a value indicating whether GenerateCode.
46.56 + /// </summary>
46.57 + public bool GenerateCode { get; set; }
46.58 +
46.59 + }
46.60 +}
46.61 \ No newline at end of file
47.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
47.2 +++ b/External/OxyPlot/OxyPlot/Foundation/CodeGenerator/CodeGenerator.cs Sat Jun 08 16:53:22 2013 +0000
47.3 @@ -0,0 +1,448 @@
47.4 +// --------------------------------------------------------------------------------------------------------------------
47.5 +// <copyright file="CodeGenerator.cs" company="OxyPlot">
47.6 +// The MIT License (MIT)
47.7 +//
47.8 +// Copyright (c) 2012 Oystein Bjorke
47.9 +//
47.10 +// Permission is hereby granted, free of charge, to any person obtaining a
47.11 +// copy of this software and associated documentation files (the
47.12 +// "Software"), to deal in the Software without restriction, including
47.13 +// without limitation the rights to use, copy, modify, merge, publish,
47.14 +// distribute, sublicense, and/or sell copies of the Software, and to
47.15 +// permit persons to whom the Software is furnished to do so, subject to
47.16 +// the following conditions:
47.17 +//
47.18 +// The above copyright notice and this permission notice shall be included
47.19 +// in all copies or substantial portions of the Software.
47.20 +//
47.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
47.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
47.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
47.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
47.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
47.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
47.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
47.28 +// </copyright>
47.29 +// <summary>
47.30 +// Generates c# code for the specified PlotModel.
47.31 +// </summary>
47.32 +// --------------------------------------------------------------------------------------------------------------------
47.33 +namespace OxyPlot
47.34 +{
47.35 + using System;
47.36 + using System.Collections;
47.37 + using System.Collections.Generic;
47.38 + using System.Globalization;
47.39 + using System.Reflection;
47.40 + using System.Text;
47.41 + using System.Text.RegularExpressions;
47.42 +
47.43 + /// <summary>
47.44 + /// Provides functionality to generate C# code for the specified <see cref="PlotModel"/>.
47.45 + /// </summary>
47.46 + /// <remarks>
47.47 + /// This is useful for creating examples or unit tests. Press Ctrl+Alt+C in a plot to copy code to the clipboard.
47.48 + /// Usage:
47.49 + /// var cg = new CodeGenerator(myPlotModel);
47.50 + /// Clipboard.SetText(cg.ToCode());
47.51 + /// </remarks>
47.52 + public class CodeGenerator
47.53 + {
47.54 + /// <summary>
47.55 + /// The sb.
47.56 + /// </summary>
47.57 + private readonly StringBuilder sb;
47.58 +
47.59 + /// <summary>
47.60 + /// The variables.
47.61 + /// </summary>
47.62 + private readonly Dictionary<string, bool> variables;
47.63 +
47.64 + /// <summary>
47.65 + /// The indent string.
47.66 + /// </summary>
47.67 + private string indentString;
47.68 +
47.69 + /// <summary>
47.70 + /// The indents.
47.71 + /// </summary>
47.72 + private int indents;
47.73 +
47.74 + /// <summary>
47.75 + /// Initializes a new instance of the <see cref="CodeGenerator"/> class.
47.76 + /// </summary>
47.77 + /// <param name="model">
47.78 + /// The model.
47.79 + /// </param>
47.80 + public CodeGenerator(PlotModel model)
47.81 + {
47.82 + this.variables = new Dictionary<string, bool>();
47.83 + this.sb = new StringBuilder();
47.84 + this.Indents = 8;
47.85 + var title = model.Title ?? "Untitled";
47.86 + this.AppendLine("[Example({0})]", title.ToCode());
47.87 + string methodName = this.MakeValidVariableName(title);
47.88 + this.AppendLine("public static PlotModel {0}()", methodName);
47.89 + this.AppendLine("{");
47.90 + this.Indents += 4;
47.91 + string modelName = this.Add(model);
47.92 + this.AddChildren(modelName, "Axes", model.Axes);
47.93 + this.AddChildren(modelName, "Series", model.Series);
47.94 + this.AddChildren(modelName, "Annotations", model.Annotations);
47.95 + this.AppendLine("return {0};", modelName);
47.96 + this.Indents -= 4;
47.97 + this.AppendLine("}");
47.98 + }
47.99 +
47.100 + /// <summary>
47.101 + /// Gets or sets Indents.
47.102 + /// </summary>
47.103 + private int Indents
47.104 + {
47.105 + get
47.106 + {
47.107 + return this.indents;
47.108 + }
47.109 +
47.110 + set
47.111 + {
47.112 + this.indents = value;
47.113 + this.indentString = new string(' ', value);
47.114 + }
47.115 + }
47.116 +
47.117 + /// <summary>
47.118 + /// Formats the code.
47.119 + /// </summary>
47.120 + /// <param name="format">
47.121 + /// The format.
47.122 + /// </param>
47.123 + /// <param name="values">
47.124 + /// The values.
47.125 + /// </param>
47.126 + /// <returns>
47.127 + /// The format code.
47.128 + /// </returns>
47.129 + public static string FormatCode(string format, params object[] values)
47.130 + {
47.131 + var encodedValues = new object[values.Length];
47.132 + for (int i = 0; i < values.Length; i++)
47.133 + {
47.134 + encodedValues[i] = values[i].ToCode();
47.135 + }
47.136 +
47.137 + return string.Format(format, encodedValues);
47.138 + }
47.139 +
47.140 + /// <summary>
47.141 + /// Formats a constructor.
47.142 + /// </summary>
47.143 + /// <param name="type">
47.144 + /// The type.
47.145 + /// </param>
47.146 + /// <param name="format">
47.147 + /// The format of the constructor arguments.
47.148 + /// </param>
47.149 + /// <param name="values">
47.150 + /// The argument values.
47.151 + /// </param>
47.152 + /// <returns>
47.153 + /// The format constructor.
47.154 + /// </returns>
47.155 + public static string FormatConstructor(Type type, string format, params object[] values)
47.156 + {
47.157 + return string.Format("new {0}({1})", type.Name, FormatCode(format, values));
47.158 + }
47.159 +
47.160 + /// <summary>
47.161 + /// Returns the c# code for this model.
47.162 + /// </summary>
47.163 + /// <returns>
47.164 + /// C# code.
47.165 + /// </returns>
47.166 + public string ToCode()
47.167 + {
47.168 + return this.sb.ToString();
47.169 + }
47.170 +
47.171 + /// <summary>
47.172 + /// Adds the specified object to the generated code.
47.173 + /// </summary>
47.174 + /// <param name="obj">
47.175 + /// The object.
47.176 + /// </param>
47.177 + /// <returns>
47.178 + /// The variable name.
47.179 + /// </returns>
47.180 + private string Add(object obj)
47.181 + {
47.182 + Type type = obj.GetType();
47.183 + object defaultInstance = Activator.CreateInstance(type);
47.184 + string varName = this.GetNewVariableName(type);
47.185 + this.variables.Add(varName, true);
47.186 + this.AppendLine("var {0} = new {1}();", varName, type.Name);
47.187 + this.SetProperties(obj, varName, defaultInstance);
47.188 + return varName;
47.189 + }
47.190 +
47.191 + /// <summary>
47.192 + /// Adds the children.
47.193 + /// </summary>
47.194 + /// <param name="name">
47.195 + /// The name.
47.196 + /// </param>
47.197 + /// <param name="collectionName">
47.198 + /// Name of the collection.
47.199 + /// </param>
47.200 + /// <param name="children">
47.201 + /// The children.
47.202 + /// </param>
47.203 + private void AddChildren(string name, string collectionName, IEnumerable children)
47.204 + {
47.205 + foreach (var child in children)
47.206 + {
47.207 + string childName = this.Add(child);
47.208 + this.AppendLine("{0}.{1}.Add({2});", name, collectionName, childName);
47.209 + }
47.210 + }
47.211 +
47.212 + /// <summary>
47.213 + /// Adds the items.
47.214 + /// </summary>
47.215 + /// <param name="name">
47.216 + /// The name.
47.217 + /// </param>
47.218 + /// <param name="list">
47.219 + /// The list.
47.220 + /// </param>
47.221 + private void AddItems(string name, IList list)
47.222 + {
47.223 + foreach (var item in list)
47.224 + {
47.225 + var code = item.ToCode();
47.226 + if (code == null)
47.227 + {
47.228 + continue;
47.229 + }
47.230 +
47.231 + this.AppendLine("{0}.Add({1});", name, code);
47.232 + }
47.233 + }
47.234 +
47.235 + /// <summary>
47.236 + /// Appends the line.
47.237 + /// </summary>
47.238 + /// <param name="format">
47.239 + /// The format string.
47.240 + /// </param>
47.241 + /// <param name="args">
47.242 + /// The args.
47.243 + /// </param>
47.244 + private void AppendLine(string format, params object[] args)
47.245 + {
47.246 + if (args.Length > 0)
47.247 + {
47.248 + this.sb.AppendLine(this.indentString + string.Format(CultureInfo.InvariantCulture, format, args));
47.249 + }
47.250 + else
47.251 + {
47.252 + this.sb.AppendLine(this.indentString + format);
47.253 + }
47.254 + }
47.255 +
47.256 + /// <summary>
47.257 + /// Determines if the two specifed lists are equal.
47.258 + /// </summary>
47.259 + /// <param name="list1">
47.260 + /// The first list.
47.261 + /// </param>
47.262 + /// <param name="list2">
47.263 + /// The second list.
47.264 + /// </param>
47.265 + /// <returns>
47.266 + /// True if all items are equal.
47.267 + /// </returns>
47.268 + private bool AreListsEqual(IList list1, IList list2)
47.269 + {
47.270 + if (list1 == null || list2 == null)
47.271 + {
47.272 + return false;
47.273 + }
47.274 +
47.275 + if (list1.Count != list2.Count)
47.276 + {
47.277 + return false;
47.278 + }
47.279 +
47.280 + for (int i = 0; i < list1.Count; i++)
47.281 + {
47.282 + if (!list1[i].Equals(list2[i]))
47.283 + {
47.284 + return false;
47.285 + }
47.286 + }
47.287 +
47.288 + return true;
47.289 + }
47.290 +
47.291 + /// <summary>
47.292 + /// Get the first attribute of the specified type.
47.293 + /// </summary>
47.294 + /// <param name="pi">
47.295 + /// The property info.
47.296 + /// </param>
47.297 + /// <typeparam name="T">
47.298 + /// The type.
47.299 + /// </typeparam>
47.300 + /// <returns>
47.301 + /// The attribute, or null if no attribute was found.
47.302 + /// </returns>
47.303 + private T GetFirstAttribute<T>(PropertyInfo pi) where T : Attribute
47.304 + {
47.305 + foreach (T a in pi.GetCustomAttributes(typeof(CodeGenerationAttribute), true))
47.306 + {
47.307 + return a;
47.308 + }
47.309 +
47.310 + return null;
47.311 + }
47.312 +
47.313 + /// <summary>
47.314 + /// Gets a new variable name of the specified type.
47.315 + /// </summary>
47.316 + /// <param name="type">
47.317 + /// The type.
47.318 + /// </param>
47.319 + /// <returns>
47.320 + /// The variable name.
47.321 + /// </returns>
47.322 + private string GetNewVariableName(Type type)
47.323 + {
47.324 + string prefix = type.Name;
47.325 + prefix = char.ToLower(prefix[0]) + prefix.Substring(1);
47.326 + int i = 1;
47.327 + while (this.variables.ContainsKey(prefix + i))
47.328 + {
47.329 + i++;
47.330 + }
47.331 +
47.332 + return prefix + i;
47.333 + }
47.334 +
47.335 + /// <summary>
47.336 + /// Makes a valid variable name of a string. Invalid characters will simply be removed.
47.337 + /// </summary>
47.338 + /// <param name="title">
47.339 + /// The title.
47.340 + /// </param>
47.341 + /// <returns>
47.342 + /// A valid variable name.
47.343 + /// </returns>
47.344 + private string MakeValidVariableName(string title)
47.345 + {
47.346 + if (title == null)
47.347 + {
47.348 + return null;
47.349 + }
47.350 +
47.351 + var regex = new Regex("[a-zA-Z_][a-zA-Z0-9_]*");
47.352 + var result = new StringBuilder();
47.353 + foreach (var c in title)
47.354 + {
47.355 + string s = c.ToString();
47.356 + if (regex.Match(s).Success)
47.357 + {
47.358 + result.Append(s);
47.359 + }
47.360 + }
47.361 +
47.362 + return result.ToString();
47.363 + }
47.364 +
47.365 + /// <summary>
47.366 + /// The set properties.
47.367 + /// </summary>
47.368 + /// <param name="instance">
47.369 + /// The instance.
47.370 + /// </param>
47.371 + /// <param name="varName">
47.372 + /// The var name.
47.373 + /// </param>
47.374 + /// <param name="defaultValues">
47.375 + /// The default values.
47.376 + /// </param>
47.377 + private void SetProperties(object instance, string varName, object defaultValues)
47.378 + {
47.379 + var instanceType = instance.GetType();
47.380 + var listsToAdd = new Dictionary<string, IList>();
47.381 + foreach (var pi in instanceType.GetProperties())
47.382 + {
47.383 + // check the [CodeGeneration] attribute
47.384 + var cga = this.GetFirstAttribute<CodeGenerationAttribute>(pi);
47.385 + if (cga != null && !cga.GenerateCode)
47.386 + {
47.387 + continue;
47.388 + }
47.389 +
47.390 + string name = varName + "." + pi.Name;
47.391 + object value = pi.GetValue(instance, null);
47.392 + object defaultValue = pi.GetValue(defaultValues, null);
47.393 +
47.394 + // check if lists are equal
47.395 + if (this.AreListsEqual(value as IList, defaultValue as IList))
47.396 + {
47.397 + continue;
47.398 + }
47.399 +
47.400 + // add items of lists
47.401 + var list = value as IList;
47.402 + if (list != null)
47.403 + {
47.404 + listsToAdd.Add(name, list);
47.405 + continue;
47.406 + }
47.407 +
47.408 + // only properties with public setters are used
47.409 + var setter = pi.GetSetMethod();
47.410 + if (setter == null || !setter.IsPublic)
47.411 + {
47.412 + continue;
47.413 + }
47.414 +
47.415 + // skip default values
47.416 + if ((value != null && value.Equals(defaultValue)) || value == defaultValue)
47.417 + {
47.418 + continue;
47.419 + }
47.420 +
47.421 + this.SetProperty(name, value);
47.422 + }
47.423 +
47.424 + // Add the items of the lists
47.425 + foreach (var kvp in listsToAdd)
47.426 + {
47.427 + var name = kvp.Key;
47.428 + var list = kvp.Value;
47.429 + this.AddItems(name, list);
47.430 + }
47.431 + }
47.432 +
47.433 + /// <summary>
47.434 + /// Sets the property.
47.435 + /// </summary>
47.436 + /// <param name="name">
47.437 + /// The property name.
47.438 + /// </param>
47.439 + /// <param name="value">
47.440 + /// The value.
47.441 + /// </param>
47.442 + private void SetProperty(string name, object value)
47.443 + {
47.444 + string code = value.ToCode();
47.445 + if (code != null)
47.446 + {
47.447 + this.AppendLine("{0} = {1};", name, code);
47.448 + }
47.449 + }
47.450 + }
47.451 +}
47.452 \ No newline at end of file
48.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
48.2 +++ b/External/OxyPlot/OxyPlot/Foundation/CodeGenerator/CodeGeneratorStringExtensions.cs Sat Jun 08 16:53:22 2013 +0000
48.3 @@ -0,0 +1,188 @@
48.4 +// --------------------------------------------------------------------------------------------------------------------
48.5 +// <copyright file="CodeGeneratorStringExtensions.cs" company="OxyPlot">
48.6 +// The MIT License (MIT)
48.7 +//
48.8 +// Copyright (c) 2012 Oystein Bjorke
48.9 +//
48.10 +// Permission is hereby granted, free of charge, to any person obtaining a
48.11 +// copy of this software and associated documentation files (the
48.12 +// "Software"), to deal in the Software without restriction, including
48.13 +// without limitation the rights to use, copy, modify, merge, publish,
48.14 +// distribute, sublicense, and/or sell copies of the Software, and to
48.15 +// permit persons to whom the Software is furnished to do so, subject to
48.16 +// the following conditions:
48.17 +//
48.18 +// The above copyright notice and this permission notice shall be included
48.19 +// in all copies or substantial portions of the Software.
48.20 +//
48.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
48.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
48.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
48.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
48.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
48.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
48.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
48.28 +// </copyright>
48.29 +// <summary>
48.30 +// The code generator string extensions.
48.31 +// </summary>
48.32 +// --------------------------------------------------------------------------------------------------------------------
48.33 +namespace OxyPlot
48.34 +{
48.35 + using System;
48.36 + using System.Globalization;
48.37 +
48.38 + /// <summary>
48.39 + /// Provides extension methods for code generation.
48.40 + /// </summary>
48.41 + public static class CodeGeneratorStringExtensions
48.42 + {
48.43 + /// <summary>
48.44 + /// Converts the value of this instance to c# code.
48.45 + /// </summary>
48.46 + /// <param name="value">
48.47 + /// The instance.
48.48 + /// </param>
48.49 + /// <returns>
48.50 + /// C# code.
48.51 + /// </returns>
48.52 + public static string ToCode(this string value)
48.53 + {
48.54 + value = value.Replace("\"", "\\\"");
48.55 + value = value.Replace("\r\n", "\\n");
48.56 + value = value.Replace("\n", "\\n");
48.57 + value = value.Replace("\t", "\\t");
48.58 + return "\"" + value + "\"";
48.59 + }
48.60 +
48.61 + /// <summary>
48.62 + /// Converts the value of this instance to c# code.
48.63 + /// </summary>
48.64 + /// <param name="value">
48.65 + /// The value.
48.66 + /// </param>
48.67 + /// <returns>
48.68 + /// C# code.
48.69 + /// </returns>
48.70 + public static string ToCode(this bool value)
48.71 + {
48.72 + return value.ToString().ToLower();
48.73 + }
48.74 +
48.75 + /// <summary>
48.76 + /// Converts the value of this instance to c# code.
48.77 + /// </summary>
48.78 + /// <param name="value">
48.79 + /// The instance.
48.80 + /// </param>
48.81 + /// <returns>
48.82 + /// C# code.
48.83 + /// </returns>
48.84 + public static string ToCode(this int value)
48.85 + {
48.86 + return value.ToString(CultureInfo.InvariantCulture);
48.87 + }
48.88 +
48.89 + /// <summary>
48.90 + /// Converts the value of this instance to c# code.
48.91 + /// </summary>
48.92 + /// <param name="value">
48.93 + /// The instance.
48.94 + /// </param>
48.95 + /// <returns>
48.96 + /// C# code.
48.97 + /// </returns>
48.98 + public static string ToCode(this Enum value)
48.99 + {
48.100 + return string.Format("{0}.{1}", value.GetType().Name, value);
48.101 + }
48.102 +
48.103 + /// <summary>
48.104 + /// Converts the value of this instance to c# code.
48.105 + /// </summary>
48.106 + /// <param name="value">
48.107 + /// The instance.
48.108 + /// </param>
48.109 + /// <returns>
48.110 + /// C# code.
48.111 + /// </returns>
48.112 + public static string ToCode(this double value)
48.113 + {
48.114 + if (double.IsNaN(value))
48.115 + {
48.116 + return "double.NaN";
48.117 + }
48.118 +
48.119 + if (double.IsPositiveInfinity(value))
48.120 + {
48.121 + return "double.PositiveInfinity";
48.122 + }
48.123 +
48.124 + if (double.IsNegativeInfinity(value))
48.125 + {
48.126 + return "double.NegativeInfinity";
48.127 + }
48.128 +
48.129 + if (value.Equals(double.MinValue))
48.130 + {
48.131 + return "double.MinValue";
48.132 + }
48.133 +
48.134 + if (value.Equals(double.MaxValue))
48.135 + {
48.136 + return "double.MaxValue";
48.137 + }
48.138 +
48.139 + return value.ToString(CultureInfo.InvariantCulture);
48.140 + }
48.141 +
48.142 + /// <summary>
48.143 + /// Converts the value of this instance to c# code.
48.144 + /// </summary>
48.145 + /// <param name="value">
48.146 + /// The instance.
48.147 + /// </param>
48.148 + /// <returns>
48.149 + /// C# code.
48.150 + /// </returns>
48.151 + public static string ToCode(this object value)
48.152 + {
48.153 + if (value == null)
48.154 + {
48.155 + return "null";
48.156 + }
48.157 +
48.158 + if (value is int)
48.159 + {
48.160 + return ((int)value).ToCode();
48.161 + }
48.162 +
48.163 + if (value is double)
48.164 + {
48.165 + return ((double)value).ToCode();
48.166 + }
48.167 +
48.168 + if (value is string)
48.169 + {
48.170 + return ((string)value).ToCode();
48.171 + }
48.172 +
48.173 + if (value is bool)
48.174 + {
48.175 + return ((bool)value).ToCode();
48.176 + }
48.177 +
48.178 + if (value is Enum)
48.179 + {
48.180 + return ((Enum)value).ToCode();
48.181 + }
48.182 +
48.183 + if (value is ICodeGenerating)
48.184 + {
48.185 + return ((ICodeGenerating)value).ToCode();
48.186 + }
48.187 +
48.188 + return null;
48.189 + }
48.190 + }
48.191 +}
48.192 \ No newline at end of file
49.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
49.2 +++ b/External/OxyPlot/OxyPlot/Foundation/CodeGenerator/ICodeGenerating.cs Sat Jun 08 16:53:22 2013 +0000
49.3 @@ -0,0 +1,45 @@
49.4 +// --------------------------------------------------------------------------------------------------------------------
49.5 +// <copyright file="ICodeGenerating.cs" company="OxyPlot">
49.6 +// The MIT License (MIT)
49.7 +//
49.8 +// Copyright (c) 2012 Oystein Bjorke
49.9 +//
49.10 +// Permission is hereby granted, free of charge, to any person obtaining a
49.11 +// copy of this software and associated documentation files (the
49.12 +// "Software"), to deal in the Software without restriction, including
49.13 +// without limitation the rights to use, copy, modify, merge, publish,
49.14 +// distribute, sublicense, and/or sell copies of the Software, and to
49.15 +// permit persons to whom the Software is furnished to do so, subject to
49.16 +// the following conditions:
49.17 +//
49.18 +// The above copyright notice and this permission notice shall be included
49.19 +// in all copies or substantial portions of the Software.
49.20 +//
49.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
49.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
49.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
49.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
49.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
49.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
49.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
49.28 +// </copyright>
49.29 +// <summary>
49.30 +// Provides functionality to generate c# code of an object.
49.31 +// </summary>
49.32 +// --------------------------------------------------------------------------------------------------------------------
49.33 +namespace OxyPlot
49.34 +{
49.35 + /// <summary>
49.36 + /// Provides functionality to generate C# code of an object.
49.37 + /// </summary>
49.38 + public interface ICodeGenerating
49.39 + {
49.40 + /// <summary>
49.41 + /// Returns c# code that generates this instance.
49.42 + /// </summary>
49.43 + /// <returns>
49.44 + /// C# code.
49.45 + /// </returns>
49.46 + string ToCode();
49.47 + }
49.48 +}
49.49 \ No newline at end of file
50.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
50.2 +++ b/External/OxyPlot/OxyPlot/Foundation/CohenSutherlandClipping.cs Sat Jun 08 16:53:22 2013 +0000
50.3 @@ -0,0 +1,298 @@
50.4 +// --------------------------------------------------------------------------------------------------------------------
50.5 +// <copyright file="CohenSutherlandClipping.cs" company="OxyPlot">
50.6 +// The MIT License (MIT)
50.7 +//
50.8 +// Copyright (c) 2012 Oystein Bjorke
50.9 +//
50.10 +// Permission is hereby granted, free of charge, to any person obtaining a
50.11 +// copy of this software and associated documentation files (the
50.12 +// "Software"), to deal in the Software without restriction, including
50.13 +// without limitation the rights to use, copy, modify, merge, publish,
50.14 +// distribute, sublicense, and/or sell copies of the Software, and to
50.15 +// permit persons to whom the Software is furnished to do so, subject to
50.16 +// the following conditions:
50.17 +//
50.18 +// The above copyright notice and this permission notice shall be included
50.19 +// in all copies or substantial portions of the Software.
50.20 +//
50.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
50.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
50.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
50.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
50.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
50.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
50.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
50.28 +// </copyright>
50.29 +// <summary>
50.30 +// Line clipping algorithm.
50.31 +// </summary>
50.32 +// --------------------------------------------------------------------------------------------------------------------
50.33 +namespace OxyPlot
50.34 +{
50.35 + /// <summary>
50.36 + /// Provides a line clipping algorithm.
50.37 + /// </summary>
50.38 + /// <remarks>
50.39 + /// See http://en.wikipedia.org/wiki/Cohen%E2%80%93Sutherland
50.40 + /// </remarks>
50.41 + public class CohenSutherlandClipping
50.42 + {
50.43 + /// <summary>
50.44 + /// The bottom code.
50.45 + /// </summary>
50.46 + private const int Bottom = 4; // 0100
50.47 +
50.48 + /// <summary>
50.49 + /// The inside code.
50.50 + /// </summary>
50.51 + private const int Inside = 0; // 0000
50.52 +
50.53 + /// <summary>
50.54 + /// The left code.
50.55 + /// </summary>
50.56 + private const int Left = 1; // 0001
50.57 +
50.58 + /// <summary>
50.59 + /// The right code.
50.60 + /// </summary>
50.61 + private const int Right = 2; // 0010
50.62 +
50.63 + /// <summary>
50.64 + /// The top code.
50.65 + /// </summary>
50.66 + private const int Top = 8; // 1000
50.67 +
50.68 + /// <summary>
50.69 + /// The x maximum.
50.70 + /// </summary>
50.71 + private readonly double xmax;
50.72 +
50.73 + /// <summary>
50.74 + /// The x minimum.
50.75 + /// </summary>
50.76 + private readonly double xmin;
50.77 +
50.78 + /// <summary>
50.79 + /// The y maximum.
50.80 + /// </summary>
50.81 + private readonly double ymax;
50.82 +
50.83 + /// <summary>
50.84 + /// The y minimum.
50.85 + /// </summary>
50.86 + private readonly double ymin;
50.87 +
50.88 + /// <summary>
50.89 + /// Initializes a new instance of the <see cref="CohenSutherlandClipping"/> class.
50.90 + /// </summary>
50.91 + /// <param name="rect">
50.92 + /// The clipping rectangle.
50.93 + /// </param>
50.94 + public CohenSutherlandClipping(OxyRect rect)
50.95 + {
50.96 + this.xmin = rect.Left;
50.97 + this.xmax = rect.Right;
50.98 + this.ymin = rect.Top;
50.99 + this.ymax = rect.Bottom;
50.100 + }
50.101 +
50.102 + /// <summary>
50.103 + /// Initializes a new instance of the <see cref="CohenSutherlandClipping"/> class.
50.104 + /// </summary>
50.105 + /// <param name="xmin">
50.106 + /// The xmin.
50.107 + /// </param>
50.108 + /// <param name="xmax">
50.109 + /// The xmax.
50.110 + /// </param>
50.111 + /// <param name="ymin">
50.112 + /// The ymin.
50.113 + /// </param>
50.114 + /// <param name="ymax">
50.115 + /// The ymax.
50.116 + /// </param>
50.117 + public CohenSutherlandClipping(double xmin, double xmax, double ymin, double ymax)
50.118 + {
50.119 + this.xmin = xmin;
50.120 + this.ymin = ymin;
50.121 + this.xmax = xmax;
50.122 + this.ymax = ymax;
50.123 + }
50.124 +
50.125 + /// <summary>
50.126 + /// Cohen–Sutherland clipping algorithm clips a line from
50.127 + /// P0 = (x0, y0) to P1 = (x1, y1) against a rectangle with
50.128 + /// diagonal from (xmin, ymin) to (xmax, ymax).
50.129 + /// </summary>
50.130 + /// <param name="x0">X coordinate of the first point.</param>
50.131 + /// <param name="y0">Y coordinate of the first point.</param>
50.132 + /// <param name="x1">X coordinate of the second point.</param>
50.133 + /// <param name="y1">Y coordinate of the second point.</param>
50.134 + /// <returns>
50.135 + /// true if the line is inside.
50.136 + /// </returns>
50.137 + public bool ClipLine(ref double x0, ref double y0, ref double x1, ref double y1)
50.138 + {
50.139 + // compute outcodes for P0, P1, and whatever point lies outside the clip rectangle
50.140 + int outcode0 = this.ComputeOutCode(x0, y0);
50.141 + int outcode1 = this.ComputeOutCode(x1, y1);
50.142 + bool accept = false;
50.143 +
50.144 + while (true)
50.145 + {
50.146 + if ((outcode0 | outcode1) == 0)
50.147 + {
50.148 + // logical or is 0. Trivially accept and get out of loop
50.149 + accept = true;
50.150 + break;
50.151 + }
50.152 +
50.153 + if ((outcode0 & outcode1) != 0)
50.154 + {
50.155 + // logical and is not 0. Trivially reject and get out of loop
50.156 + break;
50.157 + }
50.158 +
50.159 + // failed both tests, so calculate the line segment to clip
50.160 + // from an outside point to an intersection with clip edge
50.161 + double x = 0, y = 0;
50.162 +
50.163 + // At least one endpoint is outside the clip rectangle; pick it.
50.164 + int outcodeOut = outcode0 != 0 ? outcode0 : outcode1;
50.165 +
50.166 + // Now find the intersection point;
50.167 + // use formulas y = y0 + slope * (x - x0), x = x0 + (1 / slope) * (y - y0)
50.168 + if ((outcodeOut & Top) != 0)
50.169 + {
50.170 + // point is above the clip rectangle
50.171 + x = x0 + ((x1 - x0) * (this.ymax - y0) / (y1 - y0));
50.172 + y = this.ymax;
50.173 + }
50.174 + else if ((outcodeOut & Bottom) != 0)
50.175 + {
50.176 + // point is below the clip rectangle
50.177 + x = x0 + ((x1 - x0) * (this.ymin - y0) / (y1 - y0));
50.178 + y = this.ymin;
50.179 + }
50.180 + else if ((outcodeOut & Right) != 0)
50.181 + {
50.182 + // point is to the right of clip rectangle
50.183 + y = y0 + ((y1 - y0) * (this.xmax - x0) / (x1 - x0));
50.184 + x = this.xmax;
50.185 + }
50.186 + else if ((outcodeOut & Left) != 0)
50.187 + {
50.188 + // point is to the left of clip rectangle
50.189 + y = y0 + ((y1 - y0) * (this.xmin - x0) / (x1 - x0));
50.190 + x = this.xmin;
50.191 + }
50.192 +
50.193 + // Now we move outside point to intersection point to clip
50.194 + // and get ready for next pass.
50.195 + if (outcodeOut == outcode0)
50.196 + {
50.197 + x0 = x;
50.198 + y0 = y;
50.199 + outcode0 = this.ComputeOutCode(x0, y0);
50.200 + }
50.201 + else
50.202 + {
50.203 + x1 = x;
50.204 + y1 = y;
50.205 + outcode1 = this.ComputeOutCode(x1, y1);
50.206 + }
50.207 + }
50.208 +
50.209 + return accept;
50.210 + }
50.211 +
50.212 + /// <summary>
50.213 + /// Cohen–Sutherland clipping algorithm clips a line from
50.214 + /// P0 = (x0, y0) to P1 = (x1, y1) against a rectangle with
50.215 + /// diagonal from (xmin, ymin) to (xmax, ymax).
50.216 + /// </summary>
50.217 + /// <param name="s0">
50.218 + /// The s 0.
50.219 + /// </param>
50.220 + /// <param name="s1">
50.221 + /// The s 1.
50.222 + /// </param>
50.223 + /// <returns>
50.224 + /// true if the line is inside
50.225 + /// </returns>
50.226 + public bool ClipLine(ref ScreenPoint s0, ref ScreenPoint s1)
50.227 + {
50.228 + return this.ClipLine(ref s0.x, ref s0.y, ref s1.x, ref s1.y);
50.229 + }
50.230 +
50.231 + /// <summary>
50.232 + /// Determines whether the specified point is inside the rectangle.
50.233 + /// </summary>
50.234 + /// <param name="x">The x coordinate.</param>
50.235 + /// <param name="y">The y coordinate.</param>
50.236 + /// <returns>
50.237 + /// <c>true</c> if the specified point is inside; otherwise, <c>false</c>.
50.238 + /// </returns>
50.239 + public bool IsInside(double x, double y)
50.240 + {
50.241 + return this.ComputeOutCode(x, y) == Inside;
50.242 + }
50.243 +
50.244 + /// <summary>
50.245 + /// Determines whether the specified point is inside the rectangle.
50.246 + /// </summary>
50.247 + /// <param name="s">The point.</param>
50.248 + /// <returns>
50.249 + /// <c>true</c> if the specified point is inside; otherwise, <c>false</c>.
50.250 + /// </returns>
50.251 + public bool IsInside(ScreenPoint s)
50.252 + {
50.253 + return this.ComputeOutCode(s.X, s.Y) == Inside;
50.254 + }
50.255 +
50.256 + /// <summary>
50.257 + /// Computes the out code.
50.258 + /// </summary>
50.259 + /// <param name="x">
50.260 + /// The x.
50.261 + /// </param>
50.262 + /// <param name="y">
50.263 + /// The y.
50.264 + /// </param>
50.265 + /// <returns>
50.266 + /// The out code.
50.267 + /// </returns>
50.268 + /// <remarks>
50.269 + /// Compute the bit code for a point (x, y) using the clip rectangle
50.270 + /// bounded diagonally by (xmin, ymin), and (xmax, ymax)
50.271 + /// </remarks>
50.272 + private int ComputeOutCode(double x, double y)
50.273 + {
50.274 + int code = Inside; // initialized as being inside of clip window
50.275 +
50.276 + if (x < this.xmin)
50.277 + {
50.278 + // to the left of clip window
50.279 + code |= Left;
50.280 + }
50.281 + else if (x > this.xmax)
50.282 + {
50.283 + // to the right of clip window
50.284 + code |= Right;
50.285 + }
50.286 +
50.287 + if (y < this.ymin)
50.288 + {
50.289 + // below the clip window
50.290 + code |= Bottom;
50.291 + }
50.292 + else if (y > this.ymax)
50.293 + {
50.294 + // above the clip window
50.295 + code |= Top;
50.296 + }
50.297 +
50.298 + return code;
50.299 + }
50.300 + }
50.301 +}
50.302 \ No newline at end of file
51.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
51.2 +++ b/External/OxyPlot/OxyPlot/Foundation/Color.cs Sat Jun 08 16:53:22 2013 +0000
51.3 @@ -0,0 +1,55 @@
51.4 +// --------------------------------------------------------------------------------------------------------------------
51.5 +// <copyright file="Color.cs" company="OxyPlot">
51.6 +// The MIT License (MIT)
51.7 +//
51.8 +// Copyright (c) 2012 Oystein Bjorke
51.9 +//
51.10 +// Permission is hereby granted, free of charge, to any person obtaining a
51.11 +// copy of this software and associated documentation files (the
51.12 +// "Software"), to deal in the Software without restriction, including
51.13 +// without limitation the rights to use, copy, modify, merge, publish,
51.14 +// distribute, sublicense, and/or sell copies of the Software, and to
51.15 +// permit persons to whom the Software is furnished to do so, subject to
51.16 +// the following conditions:
51.17 +//
51.18 +// The above copyright notice and this permission notice shall be included
51.19 +// in all copies or substantial portions of the Software.
51.20 +//
51.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
51.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
51.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
51.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
51.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
51.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
51.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
51.28 +// </copyright>
51.29 +// --------------------------------------------------------------------------------------------------------------------
51.30 +namespace OxyPlot
51.31 +{
51.32 + public class Color
51.33 + {
51.34 + public byte A { get; set; }
51.35 + public byte R { get; set; }
51.36 + public byte G { get; set; }
51.37 + public byte B { get; set; }
51.38 +
51.39 + public static Color FromARGB(byte a, byte r, byte g, byte b)
51.40 + {
51.41 + return new Color { A = a, R = r, G = g, B = b };
51.42 + }
51.43 +
51.44 + public static Color FromRGB(byte r, byte g, byte b)
51.45 + {
51.46 + return new Color { A = 255, R = r, G = g, B = b };
51.47 + }
51.48 +
51.49 + public static Color FromAColor(byte a, Color color)
51.50 + {
51.51 + return new Color { A = a, R = color.R, G = color.G, B = color.B };
51.52 + }
51.53 + public override string ToString()
51.54 + {
51.55 + return string.Format("#{0:x2}{1:x2}{2:x2}{3:x2}", A, R, G, B);
51.56 + }
51.57 + }
51.58 +}
51.59 \ No newline at end of file
52.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
52.2 +++ b/External/OxyPlot/OxyPlot/Foundation/Colors.cs Sat Jun 08 16:53:22 2013 +0000
52.3 @@ -0,0 +1,45 @@
52.4 +// --------------------------------------------------------------------------------------------------------------------
52.5 +// <copyright file="Colors.cs" company="OxyPlot">
52.6 +// The MIT License (MIT)
52.7 +//
52.8 +// Copyright (c) 2012 Oystein Bjorke
52.9 +//
52.10 +// Permission is hereby granted, free of charge, to any person obtaining a
52.11 +// copy of this software and associated documentation files (the
52.12 +// "Software"), to deal in the Software without restriction, including
52.13 +// without limitation the rights to use, copy, modify, merge, publish,
52.14 +// distribute, sublicense, and/or sell copies of the Software, and to
52.15 +// permit persons to whom the Software is furnished to do so, subject to
52.16 +// the following conditions:
52.17 +//
52.18 +// The above copyright notice and this permission notice shall be included
52.19 +// in all copies or substantial portions of the Software.
52.20 +//
52.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
52.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
52.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
52.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
52.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
52.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
52.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
52.28 +// </copyright>
52.29 +// --------------------------------------------------------------------------------------------------------------------
52.30 +namespace OxyPlot
52.31 +{
52.32 + public static class Colors
52.33 + {
52.34 + public static readonly Color Transparent = Color.FromARGB(0, 0, 0, 0);
52.35 + public static readonly Color Black = Color.FromRGB(0, 0, 0);
52.36 + public static readonly Color White = Color.FromRGB(0xFF, 0xFF, 0xFF);
52.37 + public static readonly Color DarkGray = Color.FromRGB(0xA9, 0xA9, 0xA9);
52.38 + public static readonly Color Gray = Color.FromRGB(0x80, 0x80, 0x80);
52.39 + public static readonly Color LightGray = Color.FromRGB(0xD3, 0xD3, 0xD3);
52.40 + public static readonly Color Red = Color.FromRGB(0xFF, 0, 0);
52.41 + public static readonly Color Green = Color.FromRGB(0, 0xFF, 0);
52.42 + public static readonly Color Blue = Color.FromRGB(0, 0, 0xFF);
52.43 + public static readonly Color Orange = Color.FromRGB(0xFF, 0xA5, 0x00);
52.44 + public static readonly Color Indigo = Color.FromRGB(0x4B, 0x00, 0x82);
52.45 + public static readonly Color Violet = Color.FromRGB(0xEE, 0x82, 0xEE);
52.46 + public static readonly Color Yellow = Color.FromRGB(0xFF, 0xFF, 0x00);
52.47 + }
52.48 +}
52.49 \ No newline at end of file
53.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
53.2 +++ b/External/OxyPlot/OxyPlot/Foundation/Conrec.cs Sat Jun 08 16:53:22 2013 +0000
53.3 @@ -0,0 +1,294 @@
53.4 +// --------------------------------------------------------------------------------------------------------------------
53.5 +// <copyright file="Conrec.cs" company="OxyPlot">
53.6 +// The MIT License (MIT)
53.7 +//
53.8 +// Copyright (c) 2012 Oystein Bjorke
53.9 +//
53.10 +// Permission is hereby granted, free of charge, to any person obtaining a
53.11 +// copy of this software and associated documentation files (the
53.12 +// "Software"), to deal in the Software without restriction, including
53.13 +// without limitation the rights to use, copy, modify, merge, publish,
53.14 +// distribute, sublicense, and/or sell copies of the Software, and to
53.15 +// permit persons to whom the Software is furnished to do so, subject to
53.16 +// the following conditions:
53.17 +//
53.18 +// The above copyright notice and this permission notice shall be included
53.19 +// in all copies or substantial portions of the Software.
53.20 +//
53.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
53.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
53.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
53.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
53.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
53.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
53.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
53.28 +// </copyright>
53.29 +// <summary>
53.30 +// Creates contours from a triangular mesh.
53.31 +// </summary>
53.32 +// --------------------------------------------------------------------------------------------------------------------
53.33 +namespace OxyPlot
53.34 +{
53.35 + using System;
53.36 +
53.37 + /// <summary>
53.38 + /// Provides functionality to create contours from a triangular mesh.
53.39 + /// </summary>
53.40 + /// <remarks>
53.41 + /// <para>
53.42 + /// Ported from C / Fortran code by Paul Bourke.
53.43 + /// See <a href="http://paulbourke.net/papers/conrec/">Conrec</a> for
53.44 + /// full description of code and the original source.
53.45 + /// </para>
53.46 + /// <para>
53.47 + /// Contouring aids in visualizing three dimensional surfaces on a two dimensional
53.48 + /// medium (on paper or in this case a computer graphics screen). Two most common
53.49 + /// applications are displaying topological features of an area on a map or the air
53.50 + /// pressure on a weather map. In all cases some parameter is plotted as a function
53.51 + /// of two variables, the longitude and latitude or x and y axis. One problem with
53.52 + /// computer contouring is the process is usually CPU intensive and the algorithms
53.53 + /// often use advanced mathematical techniques making them susceptible to error.
53.54 + /// </para>
53.55 + /// </remarks>
53.56 + public static class Conrec
53.57 + {
53.58 + /// <summary>
53.59 + /// Renderer delegate
53.60 + /// </summary>
53.61 + /// <param name="x1">
53.62 + /// Start point x-coordinate
53.63 + /// </param>
53.64 + /// <param name="y1">
53.65 + /// Start point y-coordinate
53.66 + /// </param>
53.67 + /// <param name="x2">
53.68 + /// End point x-coordinate
53.69 + /// </param>
53.70 + /// <param name="y2">
53.71 + /// End point y-coordinate
53.72 + /// </param>
53.73 + /// <param name="z">
53.74 + /// Contour level
53.75 + /// </param>
53.76 + public delegate void RendererDelegate(double x1, double y1, double x2, double y2, double z);
53.77 +
53.78 + /// <summary>
53.79 + /// Contour is a contouring subroutine for rectangularily spaced data
53.80 + /// It emits calls to a line drawing subroutine supplied by the user
53.81 + /// which draws a contour map corresponding to data on a randomly
53.82 + /// spaced rectangular grid. The coordinates emitted are in the same
53.83 + /// units given in the x() and y() arrays.
53.84 + /// Any number of contour levels may be specified but they must be
53.85 + /// in order of increasing value.
53.86 + /// </summary>
53.87 + /// <param name="d">
53.88 + /// Matrix of data to contour.
53.89 + /// </param>
53.90 + /// <param name="x">
53.91 + /// Data matrix column coordinates.
53.92 + /// </param>
53.93 + /// <param name="y">
53.94 + /// Data matrix row coordinates.
53.95 + /// </param>
53.96 + /// <param name="z">
53.97 + /// Contour levels in increasing order.
53.98 + /// </param>
53.99 + /// <param name="renderer">
53.100 + /// The renderer.
53.101 + /// </param>
53.102 + public static void Contour(double[,] d, double[] x, double[] y, double[] z, RendererDelegate renderer)
53.103 + {
53.104 + double x1 = 0.0;
53.105 + double x2 = 0.0;
53.106 + double y1 = 0.0;
53.107 + double y2 = 0.0;
53.108 +
53.109 + var h = new double[5];
53.110 + var sh = new int[5];
53.111 + var xh = new double[5];
53.112 + var yh = new double[5];
53.113 +
53.114 + int ilb = d.GetLowerBound(0);
53.115 + int iub = d.GetUpperBound(0);
53.116 + int jlb = d.GetLowerBound(1);
53.117 + int jub = d.GetUpperBound(1);
53.118 + int nc = z.Length;
53.119 +
53.120 + // The indexing of im and jm should be noted as it has to start from zero
53.121 + // unlike the fortran counter part
53.122 + int[] im = { 0, 1, 1, 0 };
53.123 + int[] jm = { 0, 0, 1, 1 };
53.124 +
53.125 + // Note that castab is arranged differently from the FORTRAN code because
53.126 + // Fortran and C/C++ arrays are transposed of each other, in this case
53.127 + // it is more tricky as castab is in 3 dimension
53.128 + int[,,] castab =
53.129 + {
53.130 + { { 0, 0, 8 }, { 0, 2, 5 }, { 7, 6, 9 } }, { { 0, 3, 4 }, { 1, 3, 1 }, { 4, 3, 0 } },
53.131 + { { 9, 6, 7 }, { 5, 2, 0 }, { 8, 0, 0 } }
53.132 + };
53.133 +
53.134 + Func<int, int, double> xsect = (p1, p2) => ((h[p2] * xh[p1]) - (h[p1] * xh[p2])) / (h[p2] - h[p1]);
53.135 + Func<int, int, double> ysect = (p1, p2) => ((h[p2] * yh[p1]) - (h[p1] * yh[p2])) / (h[p2] - h[p1]);
53.136 +
53.137 + for (int j = jub - 1; j >= jlb; j--)
53.138 + {
53.139 + int i;
53.140 + for (i = ilb; i <= iub - 1; i++)
53.141 + {
53.142 + double temp1 = Math.Min(d[i, j], d[i, j + 1]);
53.143 + double temp2 = Math.Min(d[i + 1, j], d[i + 1, j + 1]);
53.144 + double dmin = Math.Min(temp1, temp2);
53.145 + temp1 = Math.Max(d[i, j], d[i, j + 1]);
53.146 + temp2 = Math.Max(d[i + 1, j], d[i + 1, j + 1]);
53.147 + double dmax = Math.Max(temp1, temp2);
53.148 +
53.149 + if (dmax >= z[0] && dmin <= z[nc - 1])
53.150 + {
53.151 + int k;
53.152 + for (k = 0; k < nc; k++)
53.153 + {
53.154 + if (z[k] >= dmin && z[k] <= dmax)
53.155 + {
53.156 + int m;
53.157 + for (m = 4; m >= 0; m--)
53.158 + {
53.159 + if (m > 0)
53.160 + {
53.161 + // The indexing of im and jm should be noted as it has to
53.162 + // start from zero
53.163 + h[m] = d[i + im[m - 1], j + jm[m - 1]] - z[k];
53.164 + xh[m] = x[i + im[m - 1]];
53.165 + yh[m] = y[j + jm[m - 1]];
53.166 + }
53.167 + else
53.168 + {
53.169 + h[0] = 0.25 * (h[1] + h[2] + h[3] + h[4]);
53.170 + xh[0] = 0.5 * (x[i] + x[i + 1]);
53.171 + yh[0] = 0.5 * (y[j] + y[j + 1]);
53.172 + }
53.173 +
53.174 + if (h[m] > 0.0)
53.175 + {
53.176 + sh[m] = 1;
53.177 + }
53.178 + else if (h[m] < 0.0)
53.179 + {
53.180 + sh[m] = -1;
53.181 + }
53.182 + else
53.183 + {
53.184 + sh[m] = 0;
53.185 + }
53.186 + }
53.187 +
53.188 + //// Note: at this stage the relative heights of the corners and the
53.189 + //// centre are in the h array, and the corresponding coordinates are
53.190 + //// in the xh and yh arrays. The centre of the box is indexed by 0
53.191 + //// and the 4 corners by 1 to 4 as shown below.
53.192 + //// Each triangle is then indexed by the parameter m, and the 3
53.193 + //// vertices of each triangle are indexed by parameters m1,m2,and
53.194 + //// m3.
53.195 + //// It is assumed that the centre of the box is always vertex 2
53.196 + //// though this isimportant only when all 3 vertices lie exactly on
53.197 + //// the same contour level, in which case only the side of the box
53.198 + //// is drawn.
53.199 + //// vertex 4 +-------------------+ vertex 3
53.200 + //// | \ / |
53.201 + //// | \ m-3 / |
53.202 + //// | \ / |
53.203 + //// | \ / |
53.204 + //// | m=2 X m=2 | the centre is vertex 0
53.205 + //// | / \ |
53.206 + //// | / \ |
53.207 + //// | / m=1 \ |
53.208 + //// | / \ |
53.209 + //// vertex 1 +-------------------+ vertex 2
53.210 +
53.211 + // Scan each triangle in the box
53.212 + for (m = 1; m <= 4; m++)
53.213 + {
53.214 + int m1 = m;
53.215 + int m2 = 0;
53.216 + int m3;
53.217 + if (m != 4)
53.218 + {
53.219 + m3 = m + 1;
53.220 + }
53.221 + else
53.222 + {
53.223 + m3 = 1;
53.224 + }
53.225 +
53.226 + int caseValue = castab[sh[m1] + 1, sh[m2] + 1, sh[m3] + 1];
53.227 + if (caseValue != 0)
53.228 + {
53.229 + switch (caseValue)
53.230 + {
53.231 + case 1: // Line between vertices 1 and 2
53.232 + x1 = xh[m1];
53.233 + y1 = yh[m1];
53.234 + x2 = xh[m2];
53.235 + y2 = yh[m2];
53.236 + break;
53.237 + case 2: // Line between vertices 2 and 3
53.238 + x1 = xh[m2];
53.239 + y1 = yh[m2];
53.240 + x2 = xh[m3];
53.241 + y2 = yh[m3];
53.242 + break;
53.243 + case 3: // Line between vertices 3 and 1
53.244 + x1 = xh[m3];
53.245 + y1 = yh[m3];
53.246 + x2 = xh[m1];
53.247 + y2 = yh[m1];
53.248 + break;
53.249 + case 4: // Line between vertex 1 and side 2-3
53.250 + x1 = xh[m1];
53.251 + y1 = yh[m1];
53.252 + x2 = xsect(m2, m3);
53.253 + y2 = ysect(m2, m3);
53.254 + break;
53.255 + case 5: // Line between vertex 2 and side 3-1
53.256 + x1 = xh[m2];
53.257 + y1 = yh[m2];
53.258 + x2 = xsect(m3, m1);
53.259 + y2 = ysect(m3, m1);
53.260 + break;
53.261 + case 6: // Line between vertex 3 and side 1-2
53.262 + x1 = xh[m3];
53.263 + y1 = yh[m3];
53.264 + x2 = xsect(m1, m2);
53.265 + y2 = ysect(m1, m2);
53.266 + break;
53.267 + case 7: // Line between sides 1-2 and 2-3
53.268 + x1 = xsect(m1, m2);
53.269 + y1 = ysect(m1, m2);
53.270 + x2 = xsect(m2, m3);
53.271 + y2 = ysect(m2, m3);
53.272 + break;
53.273 + case 8: // Line between sides 2-3 and 3-1
53.274 + x1 = xsect(m2, m3);
53.275 + y1 = ysect(m2, m3);
53.276 + x2 = xsect(m3, m1);
53.277 + y2 = ysect(m3, m1);
53.278 + break;
53.279 + case 9: // Line between sides 3-1 and 1-2
53.280 + x1 = xsect(m3, m1);
53.281 + y1 = ysect(m3, m1);
53.282 + x2 = xsect(m1, m2);
53.283 + y2 = ysect(m1, m2);
53.284 + break;
53.285 + }
53.286 +
53.287 + renderer(x1, y1, x2, y2, z[k]);
53.288 + }
53.289 + }
53.290 + }
53.291 + }
53.292 + }
53.293 + }
53.294 + }
53.295 + }
53.296 + }
53.297 +}
53.298 \ No newline at end of file
54.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
54.2 +++ b/External/OxyPlot/OxyPlot/Foundation/DataPoint.cs Sat Jun 08 16:53:22 2013 +0000
54.3 @@ -0,0 +1,136 @@
54.4 +// --------------------------------------------------------------------------------------------------------------------
54.5 +// <copyright file="DataPoint.cs" company="OxyPlot">
54.6 +// The MIT License (MIT)
54.7 +//
54.8 +// Copyright (c) 2012 Oystein Bjorke
54.9 +//
54.10 +// Permission is hereby granted, free of charge, to any person obtaining a
54.11 +// copy of this software and associated documentation files (the
54.12 +// "Software"), to deal in the Software without restriction, including
54.13 +// without limitation the rights to use, copy, modify, merge, publish,
54.14 +// distribute, sublicense, and/or sell copies of the Software, and to
54.15 +// permit persons to whom the Software is furnished to do so, subject to
54.16 +// the following conditions:
54.17 +//
54.18 +// The above copyright notice and this permission notice shall be included
54.19 +// in all copies or substantial portions of the Software.
54.20 +//
54.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
54.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
54.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
54.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
54.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
54.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
54.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
54.28 +// </copyright>
54.29 +// <summary>
54.30 +// DataPoint value type.
54.31 +// </summary>
54.32 +// --------------------------------------------------------------------------------------------------------------------
54.33 +namespace OxyPlot
54.34 +{
54.35 + using System.Diagnostics.CodeAnalysis;
54.36 +
54.37 + /// <summary>
54.38 + /// Represents a point in the data coordinate system.
54.39 + /// </summary>
54.40 + /// <remarks>
54.41 + /// <see cref="DataPoint"/>s are transformed to <see cref="ScreenPoint"/>s.
54.42 + /// </remarks>
54.43 + public struct DataPoint : IDataPoint, ICodeGenerating
54.44 + {
54.45 + /// <summary>
54.46 + /// The undefined.
54.47 + /// </summary>
54.48 + public static readonly DataPoint Undefined = new DataPoint(double.NaN, double.NaN);
54.49 +
54.50 + /// <summary>
54.51 + /// The x-coordinate.
54.52 + /// </summary>
54.53 + [SuppressMessage("StyleCop.CSharp.NamingRules", "SA1307:AccessibleFieldsMustBeginWithUpperCaseLetter",
54.54 + Justification = "Reviewed. Suppression is OK here.")]
54.55 + internal double x;
54.56 +
54.57 + /// <summary>
54.58 + /// The y-coordinate.
54.59 + /// </summary>
54.60 + [SuppressMessage("StyleCop.CSharp.NamingRules", "SA1307:AccessibleFieldsMustBeginWithUpperCaseLetter",
54.61 + Justification = "Reviewed. Suppression is OK here.")]
54.62 + internal double y;
54.63 +
54.64 + /// <summary>
54.65 + /// Initializes a new instance of the <see cref="DataPoint"/> struct.
54.66 + /// </summary>
54.67 + /// <param name="x">
54.68 + /// The x.
54.69 + /// </param>
54.70 + /// <param name="y">
54.71 + /// The y.
54.72 + /// </param>
54.73 + public DataPoint(double x, double y)
54.74 + {
54.75 + this.x = x;
54.76 + this.y = y;
54.77 + }
54.78 +
54.79 + /// <summary>
54.80 + /// Gets or sets the X.
54.81 + /// </summary>
54.82 + /// <value>
54.83 + /// The X.
54.84 + /// </value>
54.85 + public double X
54.86 + {
54.87 + get
54.88 + {
54.89 + return this.x;
54.90 + }
54.91 +
54.92 + set
54.93 + {
54.94 + this.x = value;
54.95 + }
54.96 + }
54.97 +
54.98 + /// <summary>
54.99 + /// Gets or sets the Y.
54.100 + /// </summary>
54.101 + /// <value>
54.102 + /// The Y.
54.103 + /// </value>
54.104 + public double Y
54.105 + {
54.106 + get
54.107 + {
54.108 + return this.y;
54.109 + }
54.110 +
54.111 + set
54.112 + {
54.113 + this.y = value;
54.114 + }
54.115 + }
54.116 +
54.117 + /// <summary>
54.118 + /// Returns C# code that generates this instance.
54.119 + /// </summary>
54.120 + /// <returns>
54.121 + /// The to code.
54.122 + /// </returns>
54.123 + public string ToCode()
54.124 + {
54.125 + return CodeGenerator.FormatConstructor(this.GetType(), "{0},{1}", this.x, this.y);
54.126 + }
54.127 +
54.128 + /// <summary>
54.129 + /// Returns a <see cref="System.String"/> that represents this instance.
54.130 + /// </summary>
54.131 + /// <returns>
54.132 + /// A <see cref="System.String"/> that represents this instance.
54.133 + /// </returns>
54.134 + public override string ToString()
54.135 + {
54.136 + return this.x + " " + this.y;
54.137 + }
54.138 + }
54.139 +}
54.140 \ No newline at end of file
55.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
55.2 +++ b/External/OxyPlot/OxyPlot/Foundation/DataPointConverter.cs Sat Jun 08 16:53:22 2013 +0000
55.3 @@ -0,0 +1,82 @@
55.4 +// --------------------------------------------------------------------------------------------------------------------
55.5 +// <copyright file="DataPointConverter.cs" company="OxyPlot">
55.6 +// The MIT License (MIT)
55.7 +//
55.8 +// Copyright (c) 2012 Oystein Bjorke
55.9 +//
55.10 +// Permission is hereby granted, free of charge, to any person obtaining a
55.11 +// copy of this software and associated documentation files (the
55.12 +// "Software"), to deal in the Software without restriction, including
55.13 +// without limitation the rights to use, copy, modify, merge, publish,
55.14 +// distribute, sublicense, and/or sell copies of the Software, and to
55.15 +// permit persons to whom the Software is furnished to do so, subject to
55.16 +// the following conditions:
55.17 +//
55.18 +// The above copyright notice and this permission notice shall be included
55.19 +// in all copies or substantial portions of the Software.
55.20 +//
55.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
55.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
55.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
55.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
55.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
55.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
55.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
55.28 +// </copyright>
55.29 +// <summary>
55.30 +// The DataPoint converter.
55.31 +// </summary>
55.32 +// --------------------------------------------------------------------------------------------------------------------
55.33 +namespace OxyPlot
55.34 +{
55.35 + using System;
55.36 + using System.ComponentModel;
55.37 + using System.Globalization;
55.38 +
55.39 + /// <summary>
55.40 + /// Converts a <see cref="DataPoint"/> object from one data type to another.
55.41 + /// </summary>
55.42 + public class DataPointConverter : TypeConverter
55.43 + {
55.44 + /// <summary>
55.45 + /// Returns whether this converter can convert an object of the given type to the type of this converter, using the specified context.
55.46 + /// </summary>
55.47 + /// <param name="context">An <see cref="T:System.ComponentModel.ITypeDescriptorContext" /> that provides a format context.</param>
55.48 + /// <param name="sourceType">A <see cref="T:System.Type" /> that represents the type you want to convert from.</param>
55.49 + /// <returns>
55.50 + /// true if this converter can perform the conversion; otherwise, false.
55.51 + /// </returns>
55.52 + public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType)
55.53 + {
55.54 + if (sourceType == typeof(string))
55.55 + {
55.56 + return true;
55.57 + }
55.58 +
55.59 + return base.CanConvertFrom(context, sourceType);
55.60 + }
55.61 +
55.62 + /// <summary>
55.63 + /// Converts the given object to the type of this converter, using the specified context and culture information.
55.64 + /// </summary>
55.65 + /// <param name="context">An <see cref="T:System.ComponentModel.ITypeDescriptorContext" /> that provides a format context.</param>
55.66 + /// <param name="culture">The <see cref="T:System.Globalization.CultureInfo" /> to use as the current culture.</param>
55.67 + /// <param name="value">The <see cref="T:System.Object" /> to convert.</param>
55.68 + /// <returns>
55.69 + /// An <see cref="T:System.Object" /> that represents the converted value.
55.70 + /// </returns>
55.71 + public override object ConvertFrom(ITypeDescriptorContext context, CultureInfo culture, object value)
55.72 + {
55.73 + if (value is string)
55.74 + {
55.75 + var input = (string)value;
55.76 + var xy = input.Split(',');
55.77 + double x = double.Parse(xy[0], CultureInfo.InvariantCulture);
55.78 + double y = double.Parse(xy[1], CultureInfo.InvariantCulture);
55.79 + return new DataPoint(x, y);
55.80 + }
55.81 +
55.82 + return base.ConvertFrom(context, culture, value);
55.83 + }
55.84 + }
55.85 +}
55.86 \ No newline at end of file
56.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
56.2 +++ b/External/OxyPlot/OxyPlot/Foundation/DoubleExtensions.cs Sat Jun 08 16:53:22 2013 +0000
56.3 @@ -0,0 +1,236 @@
56.4 +// --------------------------------------------------------------------------------------------------------------------
56.5 +// <copyright file="DoubleExtensions.cs" company="OxyPlot">
56.6 +// The MIT License (MIT)
56.7 +//
56.8 +// Copyright (c) 2012 Oystein Bjorke
56.9 +//
56.10 +// Permission is hereby granted, free of charge, to any person obtaining a
56.11 +// copy of this software and associated documentation files (the
56.12 +// "Software"), to deal in the Software without restriction, including
56.13 +// without limitation the rights to use, copy, modify, merge, publish,
56.14 +// distribute, sublicense, and/or sell copies of the Software, and to
56.15 +// permit persons to whom the Software is furnished to do so, subject to
56.16 +// the following conditions:
56.17 +//
56.18 +// The above copyright notice and this permission notice shall be included
56.19 +// in all copies or substantial portions of the Software.
56.20 +//
56.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
56.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
56.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
56.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
56.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
56.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
56.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
56.28 +// </copyright>
56.29 +// <summary>
56.30 +// Extension methods for double values.
56.31 +// </summary>
56.32 +// --------------------------------------------------------------------------------------------------------------------
56.33 +namespace OxyPlot
56.34 +{
56.35 + using System;
56.36 + using System.Globalization;
56.37 +
56.38 + /// <summary>
56.39 + /// Provides extension methods for the <see cref="Double"/> type.
56.40 + /// </summary>
56.41 + public static class DoubleExtensions
56.42 + {
56.43 + /// <summary>
56.44 + /// Squares the specified value.
56.45 + /// </summary>
56.46 + /// <param name="x">
56.47 + /// The value.
56.48 + /// </param>
56.49 + /// <returns>
56.50 + /// Squared value.
56.51 + /// </returns>
56.52 + public static double Squared(this double x)
56.53 + {
56.54 + return x * x;
56.55 + }
56.56 +
56.57 + /// <summary>
56.58 + /// Exponent function.
56.59 + /// </summary>
56.60 + /// <param name="x">
56.61 + /// The value.
56.62 + /// </param>
56.63 + /// <returns>
56.64 + /// The exponent.
56.65 + /// </returns>
56.66 + public static double GetExponent(this double x)
56.67 + {
56.68 + return Math.Round(Math.Log(Math.Abs(x), 10));
56.69 + }
56.70 +
56.71 + /// <summary>
56.72 + /// Mantissa function.
56.73 + /// http://en.wikipedia.org/wiki/Mantissa
56.74 + /// </summary>
56.75 + /// <param name="x">
56.76 + /// The value.
56.77 + /// </param>
56.78 + /// <returns>
56.79 + /// The mantissa.
56.80 + /// </returns>
56.81 + public static double GetMantissa(this double x)
56.82 + {
56.83 + return x / Math.Pow(10, x.GetExponent());
56.84 + }
56.85 +
56.86 + /// <summary>
56.87 + /// Removes the floating point noise.
56.88 + /// </summary>
56.89 + /// <param name="value">
56.90 + /// The value.
56.91 + /// </param>
56.92 + /// <returns>
56.93 + /// A double without noise.
56.94 + /// </returns>
56.95 + public static double RemoveNoise2(this double value)
56.96 + {
56.97 + return (double)((decimal)value);
56.98 + }
56.99 +
56.100 + /// <summary>
56.101 + /// Removes the floating point noise.
56.102 + /// </summary>
56.103 + /// <param name="value">
56.104 + /// The value.
56.105 + /// </param>
56.106 + /// <param name="maxDigits">
56.107 + /// The maximum number of digits.
56.108 + /// </param>
56.109 + /// <returns>
56.110 + /// A double without noise.
56.111 + /// </returns>
56.112 + public static double RemoveNoise(this double value, int maxDigits = 8)
56.113 + {
56.114 + return double.Parse(value.ToString("e" + maxDigits));
56.115 + }
56.116 +
56.117 + /// <summary>
56.118 + /// Removes the noise from double math.
56.119 + /// </summary>
56.120 + /// <param name="value">
56.121 + /// The value.
56.122 + /// </param>
56.123 + /// <returns>
56.124 + /// A double without noise.
56.125 + /// </returns>
56.126 + public static double RemoveNoiseFromDoubleMath(this double value)
56.127 + {
56.128 + if (value.IsZero() || Math.Abs(Math.Log10(Math.Abs(value))) < 27)
56.129 + {
56.130 + return (double)((decimal)value);
56.131 + }
56.132 +
56.133 + return double.Parse(value.ToString(CultureInfo.InvariantCulture), CultureInfo.InvariantCulture);
56.134 + }
56.135 +
56.136 + /// <summary>
56.137 + /// Determines whether the specified value is zero.
56.138 + /// </summary>
56.139 + /// <param name="value">The value.</param>
56.140 + /// <returns>
56.141 + /// <c>true</c> if the specified value is zero; otherwise, <c>false</c>.
56.142 + /// </returns>
56.143 + public static bool IsZero(this double value)
56.144 + {
56.145 + return Math.Abs(value) < double.Epsilon;
56.146 + }
56.147 +
56.148 + /// <summary>
56.149 + /// Calculates the nearest larger multiple of the specified value.
56.150 + /// </summary>
56.151 + /// <param name="value">
56.152 + /// The value.
56.153 + /// </param>
56.154 + /// <param name="step">
56.155 + /// The multiplier.
56.156 + /// </param>
56.157 + /// <returns>
56.158 + /// The multiple value.
56.159 + /// </returns>
56.160 + public static double ToUpperMultiple(this double value, double step)
56.161 + {
56.162 + var i = (int)Math.Ceiling(value / step);
56.163 + return (step * i).RemoveNoise();
56.164 + }
56.165 +
56.166 + /// <summary>
56.167 + /// Calculates the nearest smaller multiple of the specified value.
56.168 + /// </summary>
56.169 + /// <param name="value">
56.170 + /// The value.
56.171 + /// </param>
56.172 + /// <param name="step">
56.173 + /// The multiplier.
56.174 + /// </param>
56.175 + /// <returns>
56.176 + /// The multiple value.
56.177 + /// </returns>
56.178 + public static double ToLowerMultiple(this double value, double step)
56.179 + {
56.180 + var i = (int)Math.Floor(value / step);
56.181 + return (step * i).RemoveNoise();
56.182 + }
56.183 +
56.184 +#if THISISNOTINUSE
56.185 +
56.186 + // <summary>
56.187 + // Gets the mantissa and exponent.
56.188 + // </summary>
56.189 + /// <remarks>
56.190 + /// From <see cref="http://stackoverflow.com/questions/389993/extracting-mantissa-and-exponent-from-double-in-c"/>
56.191 + /// </remarks>
56.192 + /// <param name="d">The d.</param>
56.193 + /// <param name="negative">if set to <c>true</c> [negative].</param>
56.194 + /// <param name="mantissa">The mantissa.</param>
56.195 + /// <param name="exponent">The exponent.</param>
56.196 + public static void GetMantissaAndExponent(this double d, out bool negative, out long mantissa, out int exponent)
56.197 + {
56.198 + // Translate the double into sign, exponent and mantissa.
56.199 + long bits = BitConverter.DoubleToInt64Bits(d);
56.200 +
56.201 +// Note that the shift is sign-extended, hence the test against -1 not 1
56.202 + negative = (bits < 0);
56.203 + exponent = (int)((bits >> 52) & 0x7ffL);
56.204 + mantissa = bits & 0xfffffffffffffL;
56.205 +
56.206 + // Subnormal numbers; exponent is effectively one higher,
56.207 + // but there's no extra normalisation bit in the mantissa
56.208 + if (exponent == 0)
56.209 + {
56.210 + exponent++;
56.211 + }
56.212 +
56.213 +// Normal numbers; leave exponent as it is but add extra
56.214 + // bit to the front of the mantissa
56.215 + else
56.216 + {
56.217 + mantissa = mantissa | (1L << 52);
56.218 + }
56.219 +
56.220 + // Bias the exponent. It's actually biased by 1023, but we're
56.221 + // treating the mantissa as m.0 rather than 0.m, so we need
56.222 + // to subtract another 52 from it.
56.223 + exponent -= 1075;
56.224 +
56.225 + if (mantissa == 0)
56.226 + {
56.227 + return;
56.228 + }
56.229 +
56.230 + /* Normalize */
56.231 + while ((mantissa & 1) == 0)
56.232 + { /* i.e., Mantissa is even */
56.233 + mantissa >>= 1;
56.234 + exponent++;
56.235 + }
56.236 + }
56.237 +#endif
56.238 + }
56.239 +}
56.240 \ No newline at end of file
57.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
57.2 +++ b/External/OxyPlot/OxyPlot/Foundation/FontWeights.cs Sat Jun 08 16:53:22 2013 +0000
57.3 @@ -0,0 +1,48 @@
57.4 +// --------------------------------------------------------------------------------------------------------------------
57.5 +// <copyright file="FontWeights.cs" company="OxyPlot">
57.6 +// The MIT License (MIT)
57.7 +//
57.8 +// Copyright (c) 2012 Oystein Bjorke
57.9 +//
57.10 +// Permission is hereby granted, free of charge, to any person obtaining a
57.11 +// copy of this software and associated documentation files (the
57.12 +// "Software"), to deal in the Software without restriction, including
57.13 +// without limitation the rights to use, copy, modify, merge, publish,
57.14 +// distribute, sublicense, and/or sell copies of the Software, and to
57.15 +// permit persons to whom the Software is furnished to do so, subject to
57.16 +// the following conditions:
57.17 +//
57.18 +// The above copyright notice and this permission notice shall be included
57.19 +// in all copies or substantial portions of the Software.
57.20 +//
57.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
57.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
57.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
57.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
57.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
57.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
57.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
57.28 +// </copyright>
57.29 +// <summary>
57.30 +// Static font weights.
57.31 +// </summary>
57.32 +// --------------------------------------------------------------------------------------------------------------------
57.33 +namespace OxyPlot
57.34 +{
57.35 + /// <summary>
57.36 + /// Provides a set of static predefined font weight values.
57.37 + /// </summary>
57.38 + public static class FontWeights
57.39 + {
57.40 + /// <summary>
57.41 + /// Specifies a bold font weight.
57.42 + /// </summary>
57.43 + public const double Bold = 700;
57.44 +
57.45 + /// <summary>
57.46 + /// Specifies a normal font weight.
57.47 + /// </summary>
57.48 + public const double Normal = 400;
57.49 +
57.50 + }
57.51 +}
57.52 \ No newline at end of file
58.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
58.2 +++ b/External/OxyPlot/OxyPlot/Foundation/FractionHelper.cs Sat Jun 08 16:53:22 2013 +0000
58.3 @@ -0,0 +1,155 @@
58.4 +// --------------------------------------------------------------------------------------------------------------------
58.5 +// <copyright file="FractionHelper.cs" company="OxyPlot">
58.6 +// The MIT License (MIT)
58.7 +//
58.8 +// Copyright (c) 2012 Oystein Bjorke
58.9 +//
58.10 +// Permission is hereby granted, free of charge, to any person obtaining a
58.11 +// copy of this software and associated documentation files (the
58.12 +// "Software"), to deal in the Software without restriction, including
58.13 +// without limitation the rights to use, copy, modify, merge, publish,
58.14 +// distribute, sublicense, and/or sell copies of the Software, and to
58.15 +// permit persons to whom the Software is furnished to do so, subject to
58.16 +// the following conditions:
58.17 +//
58.18 +// The above copyright notice and this permission notice shall be included
58.19 +// in all copies or substantial portions of the Software.
58.20 +//
58.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
58.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
58.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
58.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
58.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
58.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
58.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
58.28 +// </copyright>
58.29 +// <summary>
58.30 +// Generates fraction strings from double values.
58.31 +// </summary>
58.32 +// --------------------------------------------------------------------------------------------------------------------
58.33 +namespace OxyPlot
58.34 +{
58.35 + using System;
58.36 + using System.Globalization;
58.37 +
58.38 + /// <summary>
58.39 + /// Provides functionality to generate fraction strings from double values.
58.40 + /// </summary>
58.41 + /// <remarks>
58.42 + /// Examples: "3/4", "PI/2"
58.43 + /// </remarks>
58.44 + public static class FractionHelper
58.45 + {
58.46 + /// <summary>
58.47 + /// Converts a double to a fraction string.
58.48 + /// </summary>
58.49 + /// <param name="value">
58.50 + /// The value.
58.51 + /// </param>
58.52 + /// <param name="unit">
58.53 + /// The unit.
58.54 + /// </param>
58.55 + /// <param name="unitSymbol">
58.56 + /// The unit symbol.
58.57 + /// </param>
58.58 + /// <param name="eps">
58.59 + /// The tolerance.
58.60 + /// </param>
58.61 + /// <param name="formatProvider">
58.62 + /// The format Provider.
58.63 + /// </param>
58.64 + /// <returns>
58.65 + /// The convert to fraction string.
58.66 + /// </returns>
58.67 + public static string ConvertToFractionString(
58.68 + double value,
58.69 + double unit = 1,
58.70 + string unitSymbol = null,
58.71 + double eps = 1e-6,
58.72 + IFormatProvider formatProvider = null)
58.73 + {
58.74 + if (Math.Abs(value) < eps)
58.75 + {
58.76 + return "0";
58.77 + }
58.78 +
58.79 + // ½, ⅝, ¾
58.80 + value /= unit;
58.81 +
58.82 + // int whole = (int)(value - (int) value);
58.83 + // int N = 10000;
58.84 + // int frac = (int) ((value - whole)*N);
58.85 + // var d = GCF(N,frac);
58.86 + for (int d = 1; d <= 64; d++)
58.87 + {
58.88 + double n = value * d;
58.89 + var ni = (int)Math.Round(n);
58.90 + if (Math.Abs(n - ni) < eps)
58.91 + {
58.92 + string nis = unitSymbol == null || ni != 1 ? ni.ToString(CultureInfo.InvariantCulture) : string.Empty;
58.93 + if (d == 1)
58.94 + {
58.95 + return string.Format("{0}{1}", nis, unitSymbol);
58.96 + }
58.97 +
58.98 + return string.Format("{0}{1}/{2}", nis, unitSymbol, d);
58.99 + }
58.100 + }
58.101 +
58.102 + return string.Format(formatProvider ?? CultureInfo.CurrentCulture, "{0}{1}", value, unitSymbol);
58.103 + }
58.104 +
58.105 + /// <summary>
58.106 + /// Finds the greates common divisor.
58.107 + /// </summary>
58.108 + /// <param name="a">
58.109 + /// The a.
58.110 + /// </param>
58.111 + /// <param name="b">
58.112 + /// The b.
58.113 + /// </param>
58.114 + /// <returns>
58.115 + /// The gcd.
58.116 + /// </returns>
58.117 + public static int gcd(int a, int b)
58.118 + {
58.119 + if (b == 0)
58.120 + {
58.121 + return a;
58.122 + }
58.123 +
58.124 + return gcd(b, a % b);
58.125 + }
58.126 +
58.127 + /// <summary>
58.128 + /// Finds the greatest common factor.
58.129 + /// </summary>
58.130 + /// <param name="x">
58.131 + /// The x.
58.132 + /// </param>
58.133 + /// <param name="y">
58.134 + /// The y.
58.135 + /// </param>
58.136 + /// <returns>
58.137 + /// The gcf.
58.138 + /// </returns>
58.139 + private static int GCF(int x, int y)
58.140 + {
58.141 + x = Math.Abs(x);
58.142 + y = Math.Abs(y);
58.143 + int z;
58.144 + do
58.145 + {
58.146 + z = x % y;
58.147 + if (z == 0)
58.148 + {
58.149 + return y;
58.150 + }
58.151 +
58.152 + x = y;
58.153 + y = z;
58.154 + }
58.155 + while (true);
58.156 + }
58.157 + }
58.158 +}
58.159 \ No newline at end of file
59.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
59.2 +++ b/External/OxyPlot/OxyPlot/Foundation/HorizontalAlignment.cs Sat Jun 08 16:53:22 2013 +0000
59.3 @@ -0,0 +1,52 @@
59.4 +// --------------------------------------------------------------------------------------------------------------------
59.5 +// <copyright file="HorizontalAlignment.cs" company="OxyPlot">
59.6 +// The MIT License (MIT)
59.7 +//
59.8 +// Copyright (c) 2012 Oystein Bjorke
59.9 +//
59.10 +// Permission is hereby granted, free of charge, to any person obtaining a
59.11 +// copy of this software and associated documentation files (the
59.12 +// "Software"), to deal in the Software without restriction, including
59.13 +// without limitation the rights to use, copy, modify, merge, publish,
59.14 +// distribute, sublicense, and/or sell copies of the Software, and to
59.15 +// permit persons to whom the Software is furnished to do so, subject to
59.16 +// the following conditions:
59.17 +//
59.18 +// The above copyright notice and this permission notice shall be included
59.19 +// in all copies or substantial portions of the Software.
59.20 +//
59.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
59.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
59.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
59.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
59.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
59.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
59.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
59.28 +// </copyright>
59.29 +// <summary>
59.30 +// Horizontal text alignment.
59.31 +// </summary>
59.32 +// --------------------------------------------------------------------------------------------------------------------
59.33 +namespace OxyPlot
59.34 +{
59.35 + /// <summary>
59.36 + /// Specifies the horizontal alignment.
59.37 + /// </summary>
59.38 + public enum HorizontalAlignment
59.39 + {
59.40 + /// <summary>
59.41 + /// Aligned to the left.
59.42 + /// </summary>
59.43 + Left = -1,
59.44 +
59.45 + /// <summary>
59.46 + /// Aligned in the center.
59.47 + /// </summary>
59.48 + Center = 0,
59.49 +
59.50 + /// <summary>
59.51 + /// Aligned to the right.
59.52 + /// </summary>
59.53 + Right = 1
59.54 + }
59.55 +}
59.56 \ No newline at end of file
60.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
60.2 +++ b/External/OxyPlot/OxyPlot/Foundation/IDataPoint.cs Sat Jun 08 16:53:22 2013 +0000
60.3 @@ -0,0 +1,49 @@
60.4 +// --------------------------------------------------------------------------------------------------------------------
60.5 +// <copyright file="IDataPoint.cs" company="OxyPlot">
60.6 +// The MIT License (MIT)
60.7 +//
60.8 +// Copyright (c) 2012 Oystein Bjorke
60.9 +//
60.10 +// Permission is hereby granted, free of charge, to any person obtaining a
60.11 +// copy of this software and associated documentation files (the
60.12 +// "Software"), to deal in the Software without restriction, including
60.13 +// without limitation the rights to use, copy, modify, merge, publish,
60.14 +// distribute, sublicense, and/or sell copies of the Software, and to
60.15 +// permit persons to whom the Software is furnished to do so, subject to
60.16 +// the following conditions:
60.17 +//
60.18 +// The above copyright notice and this permission notice shall be included
60.19 +// in all copies or substantial portions of the Software.
60.20 +//
60.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
60.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
60.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
60.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
60.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
60.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
60.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
60.28 +// </copyright>
60.29 +// <summary>
60.30 +// DataPoint interface.
60.31 +// </summary>
60.32 +// --------------------------------------------------------------------------------------------------------------------
60.33 +namespace OxyPlot
60.34 +{
60.35 + /// <summary>
60.36 + /// Defines a point.
60.37 + /// </summary>
60.38 + public interface IDataPoint
60.39 + {
60.40 + /// <summary>
60.41 + /// Gets or sets the x-coordinate.
60.42 + /// </summary>
60.43 + /// <value>The x-coordinate.</value>
60.44 + double X { get; set; }
60.45 +
60.46 + /// <summary>
60.47 + /// Gets or sets the y-coordinate.
60.48 + /// </summary>
60.49 + /// <value>The y-coordinate.</value>
60.50 + double Y { get; set; }
60.51 + }
60.52 +}
60.53 \ No newline at end of file
61.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
61.2 +++ b/External/OxyPlot/OxyPlot/Foundation/IDataPointProvider.cs Sat Jun 08 16:53:22 2013 +0000
61.3 @@ -0,0 +1,45 @@
61.4 +// --------------------------------------------------------------------------------------------------------------------
61.5 +// <copyright file="IDataPointProvider.cs" company="OxyPlot">
61.6 +// The MIT License (MIT)
61.7 +//
61.8 +// Copyright (c) 2012 Oystein Bjorke
61.9 +//
61.10 +// Permission is hereby granted, free of charge, to any person obtaining a
61.11 +// copy of this software and associated documentation files (the
61.12 +// "Software"), to deal in the Software without restriction, including
61.13 +// without limitation the rights to use, copy, modify, merge, publish,
61.14 +// distribute, sublicense, and/or sell copies of the Software, and to
61.15 +// permit persons to whom the Software is furnished to do so, subject to
61.16 +// the following conditions:
61.17 +//
61.18 +// The above copyright notice and this permission notice shall be included
61.19 +// in all copies or substantial portions of the Software.
61.20 +//
61.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
61.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
61.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
61.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
61.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
61.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
61.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
61.28 +// </copyright>
61.29 +// <summary>
61.30 +// Provides functionality to create data points for items in an <see cref="ItemsSeries"/>.
61.31 +// </summary>
61.32 +// --------------------------------------------------------------------------------------------------------------------
61.33 +namespace OxyPlot
61.34 +{
61.35 + /// <summary>
61.36 + /// Provides functionality to create data points.
61.37 + /// </summary>
61.38 + public interface IDataPointProvider
61.39 + {
61.40 + /// <summary>
61.41 + /// Gets the data point.
61.42 + /// </summary>
61.43 + /// <returns>
61.44 + /// The data point.
61.45 + /// </returns>
61.46 + DataPoint GetDataPoint();
61.47 + }
61.48 +}
61.49 \ No newline at end of file
62.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
62.2 +++ b/External/OxyPlot/OxyPlot/Foundation/LineStyle.cs Sat Jun 08 16:53:22 2013 +0000
62.3 @@ -0,0 +1,97 @@
62.4 +// --------------------------------------------------------------------------------------------------------------------
62.5 +// <copyright file="LineStyle.cs" company="OxyPlot">
62.6 +// The MIT License (MIT)
62.7 +//
62.8 +// Copyright (c) 2012 Oystein Bjorke
62.9 +//
62.10 +// Permission is hereby granted, free of charge, to any person obtaining a
62.11 +// copy of this software and associated documentation files (the
62.12 +// "Software"), to deal in the Software without restriction, including
62.13 +// without limitation the rights to use, copy, modify, merge, publish,
62.14 +// distribute, sublicense, and/or sell copies of the Software, and to
62.15 +// permit persons to whom the Software is furnished to do so, subject to
62.16 +// the following conditions:
62.17 +//
62.18 +// The above copyright notice and this permission notice shall be included
62.19 +// in all copies or substantial portions of the Software.
62.20 +//
62.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
62.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
62.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
62.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
62.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
62.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
62.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
62.28 +// </copyright>
62.29 +// <summary>
62.30 +// Enumeration of line styles.
62.31 +// </summary>
62.32 +// --------------------------------------------------------------------------------------------------------------------
62.33 +namespace OxyPlot
62.34 +{
62.35 + /// <summary>
62.36 + /// Specifies the style of a line.
62.37 + /// </summary>
62.38 + public enum LineStyle
62.39 + {
62.40 + /// <summary>
62.41 + /// The solid line style.
62.42 + /// </summary>
62.43 + Solid,
62.44 +
62.45 + /// <summary>
62.46 + /// The dash line style.
62.47 + /// </summary>
62.48 + Dash,
62.49 +
62.50 + /// <summary>
62.51 + /// The dot line style.
62.52 + /// </summary>
62.53 + Dot,
62.54 +
62.55 + /// <summary>
62.56 + /// The dash dot line style.
62.57 + /// </summary>
62.58 + DashDot,
62.59 +
62.60 + /// <summary>
62.61 + /// The dash dash dot line style.
62.62 + /// </summary>
62.63 + DashDashDot,
62.64 +
62.65 + /// <summary>
62.66 + /// The dash dot dot line style.
62.67 + /// </summary>
62.68 + DashDotDot,
62.69 +
62.70 + /// <summary>
62.71 + /// The dash dash dot dot line style.
62.72 + /// </summary>
62.73 + DashDashDotDot,
62.74 +
62.75 + /// <summary>
62.76 + /// The long dash line style.
62.77 + /// </summary>
62.78 + LongDash,
62.79 +
62.80 + /// <summary>
62.81 + /// The long dash dot line style.
62.82 + /// </summary>
62.83 + LongDashDot,
62.84 +
62.85 + /// <summary>
62.86 + /// The long dash dot dot line style.
62.87 + /// </summary>
62.88 + LongDashDotDot,
62.89 +
62.90 + /// <summary>
62.91 + /// The hidden line style.
62.92 + /// </summary>
62.93 + None,
62.94 +
62.95 + /// <summary>
62.96 + /// The undefined line style.
62.97 + /// </summary>
62.98 + Undefined
62.99 + }
62.100 +}
62.101 \ No newline at end of file
63.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
63.2 +++ b/External/OxyPlot/OxyPlot/Foundation/LineStyleHelper.cs Sat Jun 08 16:53:22 2013 +0000
63.3 @@ -0,0 +1,76 @@
63.4 +// --------------------------------------------------------------------------------------------------------------------
63.5 +// <copyright file="LineStyleHelper.cs" company="OxyPlot">
63.6 +// The MIT License (MIT)
63.7 +//
63.8 +// Copyright (c) 2012 Oystein Bjorke
63.9 +//
63.10 +// Permission is hereby granted, free of charge, to any person obtaining a
63.11 +// copy of this software and associated documentation files (the
63.12 +// "Software"), to deal in the Software without restriction, including
63.13 +// without limitation the rights to use, copy, modify, merge, publish,
63.14 +// distribute, sublicense, and/or sell copies of the Software, and to
63.15 +// permit persons to whom the Software is furnished to do so, subject to
63.16 +// the following conditions:
63.17 +//
63.18 +// The above copyright notice and this permission notice shall be included
63.19 +// in all copies or substantial portions of the Software.
63.20 +//
63.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
63.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
63.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
63.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
63.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
63.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
63.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
63.28 +// </copyright>
63.29 +// <summary>
63.30 +// Converts from LineStyle to stroke dash array.
63.31 +// </summary>
63.32 +// --------------------------------------------------------------------------------------------------------------------
63.33 +namespace OxyPlot
63.34 +{
63.35 + /// <summary>
63.36 + /// Provides functionality to convert from LineStyle to a stroke dash array.
63.37 + /// </summary>
63.38 + public static class LineStyleHelper
63.39 + {
63.40 + /// <summary>
63.41 + /// Gets the stroke dash array for a given <see cref="LineStyle"/>.
63.42 + /// </summary>
63.43 + /// <param name="style">
63.44 + /// The line style.
63.45 + /// </param>
63.46 + /// <returns>
63.47 + /// A dash array.
63.48 + /// </returns>
63.49 + public static double[] GetDashArray(this LineStyle style)
63.50 + {
63.51 + switch (style)
63.52 + {
63.53 + case LineStyle.Solid:
63.54 + return null;
63.55 + case LineStyle.Dash:
63.56 + return new double[] { 4, 1 };
63.57 + case LineStyle.Dot:
63.58 + return new double[] { 1, 1 };
63.59 + case LineStyle.DashDot:
63.60 + return new double[] { 4, 1, 1, 1 };
63.61 + case LineStyle.DashDashDot:
63.62 + return new double[] { 4, 1, 4, 1, 1, 1 };
63.63 + case LineStyle.DashDotDot:
63.64 + return new double[] { 4, 1, 1, 1, 1, 1 };
63.65 + case LineStyle.DashDashDotDot:
63.66 + return new double[] { 4, 1, 4, 1, 1, 1, 1, 1 };
63.67 + case LineStyle.LongDash:
63.68 + return new double[] { 10, 1 };
63.69 + case LineStyle.LongDashDot:
63.70 + return new double[] { 10, 1, 1, 1 };
63.71 + case LineStyle.LongDashDotDot:
63.72 + return new double[] { 10, 1, 1, 1, 1, 1 };
63.73 + default:
63.74 + return null;
63.75 + }
63.76 + }
63.77 +
63.78 + }
63.79 +}
63.80 \ No newline at end of file
64.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
64.2 +++ b/External/OxyPlot/OxyPlot/Foundation/ListFiller.cs Sat Jun 08 16:53:22 2013 +0000
64.3 @@ -0,0 +1,145 @@
64.4 +// --------------------------------------------------------------------------------------------------------------------
64.5 +// <copyright file="ListFiller.cs" company="OxyPlot">
64.6 +// The MIT License (MIT)
64.7 +//
64.8 +// Copyright (c) 2012 Oystein Bjorke
64.9 +//
64.10 +// Permission is hereby granted, free of charge, to any person obtaining a
64.11 +// copy of this software and associated documentation files (the
64.12 +// "Software"), to deal in the Software without restriction, including
64.13 +// without limitation the rights to use, copy, modify, merge, publish,
64.14 +// distribute, sublicense, and/or sell copies of the Software, and to
64.15 +// permit persons to whom the Software is furnished to do so, subject to
64.16 +// the following conditions:
64.17 +//
64.18 +// The above copyright notice and this permission notice shall be included
64.19 +// in all copies or substantial portions of the Software.
64.20 +//
64.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
64.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
64.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
64.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
64.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
64.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
64.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
64.28 +// </copyright>
64.29 +// --------------------------------------------------------------------------------------------------------------------
64.30 +namespace OxyPlot
64.31 +{
64.32 + using System;
64.33 + using System.Collections;
64.34 + using System.Collections.Generic;
64.35 + using System.Reflection;
64.36 +
64.37 + /// <summary>
64.38 + /// Provides functionality to fill a list by specified properties of another list.
64.39 + /// </summary>
64.40 + /// <remarks>
64.41 + /// This class uses reflection.
64.42 + /// </remarks>
64.43 + /// <typeparam name="T">
64.44 + /// The target list item type.
64.45 + /// </typeparam>
64.46 + public class ListFiller<T>
64.47 + where T : class, new()
64.48 + {
64.49 + /// <summary>
64.50 + /// The properties.
64.51 + /// </summary>
64.52 + private readonly Dictionary<string, Action<T, object>> properties;
64.53 +
64.54 + /// <summary>
64.55 + /// Initializes a new instance of the <see cref="ListFiller{T}" /> class.
64.56 + /// </summary>
64.57 + public ListFiller()
64.58 + {
64.59 + this.properties = new Dictionary<string, Action<T, object>>();
64.60 + }
64.61 +
64.62 + /// <summary>
64.63 + /// Adds a setter for the specified property.
64.64 + /// </summary>
64.65 + /// <param name="propertyName">
64.66 + /// Name of the property.
64.67 + /// </param>
64.68 + /// <param name="setter">
64.69 + /// The setter.
64.70 + /// </param>
64.71 + public void Add(string propertyName, Action<T, object> setter)
64.72 + {
64.73 + if (string.IsNullOrEmpty(propertyName))
64.74 + {
64.75 + return;
64.76 + }
64.77 +
64.78 + this.properties.Add(propertyName, setter);
64.79 + }
64.80 +
64.81 + /// <summary>
64.82 + /// Fills the specified target list.
64.83 + /// </summary>
64.84 + /// <param name="target">The target.</param>
64.85 + /// <param name="source">The source.</param>
64.86 + public void FillT(IList<T> target, IEnumerable source)
64.87 + {
64.88 + this.Fill((IList)target, source);
64.89 + }
64.90 +
64.91 + /// <summary>
64.92 + /// Fills the specified target list.
64.93 + /// </summary>
64.94 + /// <param name="target">
64.95 + /// The target.
64.96 + /// </param>
64.97 + /// <param name="source">
64.98 + /// The source list.
64.99 + /// </param>
64.100 + public void Fill(IList target, IEnumerable source)
64.101 + {
64.102 + PropertyInfo[] pi = null;
64.103 + Type t = null;
64.104 + foreach (var sourceItem in source)
64.105 + {
64.106 + if (pi == null || sourceItem.GetType() != t)
64.107 + {
64.108 + t = sourceItem.GetType();
64.109 + pi = new PropertyInfo[this.properties.Count];
64.110 + int i = 0;
64.111 + foreach (var p in this.properties)
64.112 + {
64.113 + if (string.IsNullOrEmpty(p.Key))
64.114 + {
64.115 + i++;
64.116 + continue;
64.117 + }
64.118 +
64.119 + pi[i] = t.GetProperty(p.Key);
64.120 + if (pi[i] == null)
64.121 + {
64.122 + throw new InvalidOperationException(
64.123 + string.Format("Could not find field {0} on type {1}", p.Key, t));
64.124 + }
64.125 +
64.126 + i++;
64.127 + }
64.128 + }
64.129 +
64.130 + var item = new T();
64.131 +
64.132 + int j = 0;
64.133 + foreach (var p in this.properties)
64.134 + {
64.135 + if (pi[j] != null)
64.136 + {
64.137 + var value = pi[j].GetValue(sourceItem, null);
64.138 + p.Value(item, value);
64.139 + }
64.140 +
64.141 + j++;
64.142 + }
64.143 +
64.144 + target.Add(item);
64.145 + }
64.146 + }
64.147 + }
64.148 +}
64.149 \ No newline at end of file
65.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
65.2 +++ b/External/OxyPlot/OxyPlot/Foundation/MarkerType.cs Sat Jun 08 16:53:22 2013 +0000
65.3 @@ -0,0 +1,91 @@
65.4 +// --------------------------------------------------------------------------------------------------------------------
65.5 +// <copyright file="MarkerType.cs" company="OxyPlot">
65.6 +// The MIT License (MIT)
65.7 +//
65.8 +// Copyright (c) 2012 Oystein Bjorke
65.9 +//
65.10 +// Permission is hereby granted, free of charge, to any person obtaining a
65.11 +// copy of this software and associated documentation files (the
65.12 +// "Software"), to deal in the Software without restriction, including
65.13 +// without limitation the rights to use, copy, modify, merge, publish,
65.14 +// distribute, sublicense, and/or sell copies of the Software, and to
65.15 +// permit persons to whom the Software is furnished to do so, subject to
65.16 +// the following conditions:
65.17 +//
65.18 +// The above copyright notice and this permission notice shall be included
65.19 +// in all copies or substantial portions of the Software.
65.20 +//
65.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
65.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
65.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
65.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
65.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
65.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
65.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
65.28 +// </copyright>
65.29 +// <summary>
65.30 +// Enumeration of marker types.
65.31 +// </summary>
65.32 +// --------------------------------------------------------------------------------------------------------------------
65.33 +namespace OxyPlot
65.34 +{
65.35 + /// <summary>
65.36 + /// Specifies the marker type.
65.37 + /// </summary>
65.38 + public enum MarkerType
65.39 + {
65.40 + /// <summary>
65.41 + /// Do not render markers.
65.42 + /// </summary>
65.43 + None,
65.44 +
65.45 + /// <summary>
65.46 + /// Render markers as circles.
65.47 + /// </summary>
65.48 + Circle,
65.49 +
65.50 + /// <summary>
65.51 + /// Render markers as squares.
65.52 + /// </summary>
65.53 + Square,
65.54 +
65.55 + /// <summary>
65.56 + /// Render markers as diamonds.
65.57 + /// </summary>
65.58 + Diamond,
65.59 +
65.60 + /// <summary>
65.61 + /// Render markers as triangles.
65.62 + /// </summary>
65.63 + Triangle,
65.64 +
65.65 + /// <summary>
65.66 + /// Render markers as crosses (note: this marker type requires the stroke color to be set).
65.67 + /// </summary>
65.68 + /// <remarks>
65.69 + /// This marker type requires the stroke color to be set.
65.70 + /// </remarks>
65.71 + Cross,
65.72 +
65.73 + /// <summary>
65.74 + /// Renders markers as plus signs (note: this marker type requires the stroke color to be set).
65.75 + /// </summary>
65.76 + /// <remarks>
65.77 + /// This marker type requires the stroke color to be set.
65.78 + /// </remarks>
65.79 + Plus,
65.80 +
65.81 + /// <summary>
65.82 + /// Renders markers as stars (note: this marker type requires the stroke color to be set).
65.83 + /// </summary>
65.84 + /// <remarks>
65.85 + /// This marker type requires the stroke color to be set.
65.86 + /// </remarks>
65.87 + Star,
65.88 +
65.89 + /// <summary>
65.90 + /// Render markers by a custom shape (defined by outline).
65.91 + /// </summary>
65.92 + Custom
65.93 + }
65.94 +}
65.95 \ No newline at end of file
66.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
66.2 +++ b/External/OxyPlot/OxyPlot/Foundation/OxyColor.cs Sat Jun 08 16:53:22 2013 +0000
66.3 @@ -0,0 +1,626 @@
66.4 +// --------------------------------------------------------------------------------------------------------------------
66.5 +// <copyright file="OxyColor.cs" company="OxyPlot">
66.6 +// The MIT License (MIT)
66.7 +//
66.8 +// Copyright (c) 2012 Oystein Bjorke
66.9 +//
66.10 +// Permission is hereby granted, free of charge, to any person obtaining a
66.11 +// copy of this software and associated documentation files (the
66.12 +// "Software"), to deal in the Software without restriction, including
66.13 +// without limitation the rights to use, copy, modify, merge, publish,
66.14 +// distribute, sublicense, and/or sell copies of the Software, and to
66.15 +// permit persons to whom the Software is furnished to do so, subject to
66.16 +// the following conditions:
66.17 +//
66.18 +// The above copyright notice and this permission notice shall be included
66.19 +// in all copies or substantial portions of the Software.
66.20 +//
66.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
66.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
66.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
66.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
66.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
66.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
66.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
66.28 +// </copyright>
66.29 +// <summary>
66.30 +// Describes a color in terms of alpha, red, green, and blue channels.
66.31 +// </summary>
66.32 +// --------------------------------------------------------------------------------------------------------------------
66.33 +namespace OxyPlot
66.34 +{
66.35 + using System;
66.36 + using System.ComponentModel;
66.37 + using System.Globalization;
66.38 + using System.Linq;
66.39 + using System.Reflection;
66.40 +
66.41 + /// <summary>
66.42 + /// Describes a color in terms of alpha, red, green, and blue channels.
66.43 + /// </summary>
66.44 + public class OxyColor : ICodeGenerating
66.45 + {
66.46 + /// <summary>
66.47 + /// Gets or sets the alpha value.
66.48 + /// </summary>
66.49 + /// <value> The alpha value. </value>
66.50 + public byte A { get; set; }
66.51 +
66.52 + /// <summary>
66.53 + /// Gets or sets the blue value.
66.54 + /// </summary>
66.55 + /// <value> The blue value. </value>
66.56 + public byte B { get; set; }
66.57 +
66.58 + /// <summary>
66.59 + /// Gets or sets the green value.
66.60 + /// </summary>
66.61 + /// <value> The green value. </value>
66.62 + public byte G { get; set; }
66.63 +
66.64 + /// <summary>
66.65 + /// Gets or sets the red value.
66.66 + /// </summary>
66.67 + /// <value> The red value. </value>
66.68 + public byte R { get; set; }
66.69 +
66.70 + /// <summary>
66.71 + /// Parse a string.
66.72 + /// </summary>
66.73 + /// <param name="value">
66.74 + /// The string in the format "#FFFFFF00" or "255,200,180,50".
66.75 + /// </param>
66.76 + /// <returns>
66.77 + /// The OxyColor.
66.78 + /// </returns>
66.79 + /// <exception cref="System.FormatException">
66.80 + /// Invalid format.
66.81 + /// </exception>
66.82 + public static OxyColor Parse(string value)
66.83 + {
66.84 + value = value.Trim();
66.85 + if (value.StartsWith("#"))
66.86 + {
66.87 + value = value.Trim('#');
66.88 + var u = uint.Parse(value, NumberStyles.HexNumber, CultureInfo.InvariantCulture);
66.89 + if (value.Length < 8)
66.90 + {
66.91 + // alpha value was not specified
66.92 + u += 0xFF000000;
66.93 + }
66.94 +
66.95 + return FromUInt32(u);
66.96 + }
66.97 +
66.98 + var values = value.Split(',');
66.99 + if (values.Length < 3 || values.Length > 4)
66.100 + {
66.101 + throw new FormatException("Invalid format.");
66.102 + }
66.103 +
66.104 + var i = 0;
66.105 +
66.106 + byte alpha = 255;
66.107 + if (values.Length > 3)
66.108 + {
66.109 + alpha = byte.Parse(values[i++], CultureInfo.InvariantCulture);
66.110 + }
66.111 +
66.112 + var red = byte.Parse(values[i++], CultureInfo.InvariantCulture);
66.113 + var green = byte.Parse(values[i++], CultureInfo.InvariantCulture);
66.114 + var blue = byte.Parse(values[i], CultureInfo.InvariantCulture);
66.115 + return FromArgb(alpha, red, green, blue);
66.116 + }
66.117 +
66.118 + /// <summary>
66.119 + /// Calculates the difference between two <see cref="OxyColor"/>s
66.120 + /// </summary>
66.121 + /// <param name="c1">
66.122 + /// The first color.
66.123 + /// </param>
66.124 + /// <param name="c2">
66.125 + /// The second color.
66.126 + /// </param>
66.127 + /// <returns>
66.128 + /// L2-norm in RGBA space
66.129 + /// </returns>
66.130 + public static double ColorDifference(OxyColor c1, OxyColor c2)
66.131 + {
66.132 + // http://en.wikipedia.org/wiki/OxyColor_difference
66.133 + // http://mathworld.wolfram.com/L2-Norm.html
66.134 + double dr = (c1.R - c2.R) / 255.0;
66.135 + double dg = (c1.G - c2.G) / 255.0;
66.136 + double db = (c1.B - c2.B) / 255.0;
66.137 + double da = (c1.A - c2.A) / 255.0;
66.138 + double e = (dr * dr) + (dg * dg) + (db * db) + (da * da);
66.139 + return Math.Sqrt(e);
66.140 + }
66.141 +
66.142 + /// <summary>
66.143 + /// Convert an <see cref="uint"/> to a <see cref="OxyColor"/>.
66.144 + /// </summary>
66.145 + /// <param name="color">
66.146 + /// The unsigned integer color value.
66.147 + /// </param>
66.148 + /// <returns>
66.149 + /// The <see cref="OxyColor"/>.
66.150 + /// </returns>
66.151 + public static OxyColor FromUInt32(uint color)
66.152 + {
66.153 + var a = (byte)(color >> 24);
66.154 + var r = (byte)(color >> 16);
66.155 + var g = (byte)(color >> 8);
66.156 + var b = (byte)(color >> 0);
66.157 + return FromArgb(a, r, g, b);
66.158 + }
66.159 +
66.160 + /// <summary>
66.161 + /// Creates a OxyColor from the specified HSV array.
66.162 + /// </summary>
66.163 + /// <param name="hsv">
66.164 + /// The HSV value array.
66.165 + /// </param>
66.166 + /// <returns>
66.167 + /// A OxyColor.
66.168 + /// </returns>
66.169 + public static OxyColor FromHsv(double[] hsv)
66.170 + {
66.171 + if (hsv.Length != 3)
66.172 + {
66.173 + throw new InvalidOperationException("Wrong length of hsv array.");
66.174 + }
66.175 +
66.176 + return FromHsv(hsv[0], hsv[1], hsv[2]);
66.177 + }
66.178 +
66.179 + /// <summary>
66.180 + /// Convert from HSV to <see cref="OxyColor"/>
66.181 + /// http://en.wikipedia.org/wiki/HSL_Color_space
66.182 + /// </summary>
66.183 + /// <param name="hue">
66.184 + /// The hue value [0,1]
66.185 + /// </param>
66.186 + /// <param name="sat">
66.187 + /// The saturation value [0,1]
66.188 + /// </param>
66.189 + /// <param name="val">
66.190 + /// The intensity value [0,1]
66.191 + /// </param>
66.192 + /// <returns>
66.193 + /// The <see cref="OxyColor"/>.
66.194 + /// </returns>
66.195 + public static OxyColor FromHsv(double hue, double sat, double val)
66.196 + {
66.197 + double g, b;
66.198 + double r = g = b = 0;
66.199 +
66.200 + if (sat.Equals(0))
66.201 + {
66.202 + // Gray scale
66.203 + r = g = b = val;
66.204 + }
66.205 + else
66.206 + {
66.207 + if (hue.Equals(1))
66.208 + {
66.209 + hue = 0;
66.210 + }
66.211 +
66.212 + hue *= 6.0;
66.213 + int i = (int)Math.Floor(hue);
66.214 + double f = hue - i;
66.215 + double aa = val * (1 - sat);
66.216 + double bb = val * (1 - (sat * f));
66.217 + double cc = val * (1 - (sat * (1 - f)));
66.218 + switch (i)
66.219 + {
66.220 + case 0:
66.221 + r = val;
66.222 + g = cc;
66.223 + b = aa;
66.224 + break;
66.225 + case 1:
66.226 + r = bb;
66.227 + g = val;
66.228 + b = aa;
66.229 + break;
66.230 + case 2:
66.231 + r = aa;
66.232 + g = val;
66.233 + b = cc;
66.234 + break;
66.235 + case 3:
66.236 + r = aa;
66.237 + g = bb;
66.238 + b = val;
66.239 + break;
66.240 + case 4:
66.241 + r = cc;
66.242 + g = aa;
66.243 + b = val;
66.244 + break;
66.245 + case 5:
66.246 + r = val;
66.247 + g = aa;
66.248 + b = bb;
66.249 + break;
66.250 + }
66.251 + }
66.252 +
66.253 + return FromRgb((byte)(r * 255), (byte)(g * 255), (byte)(b * 255));
66.254 + }
66.255 +
66.256 + /// <summary>
66.257 + /// Calculate the difference in hue between two <see cref="OxyColor"/>s.
66.258 + /// </summary>
66.259 + /// <param name="c1">
66.260 + /// The first color.
66.261 + /// </param>
66.262 + /// <param name="c2">
66.263 + /// The second color.
66.264 + /// </param>
66.265 + /// <returns>
66.266 + /// The hue difference.
66.267 + /// </returns>
66.268 + public static double HueDifference(OxyColor c1, OxyColor c2)
66.269 + {
66.270 + var hsv1 = c1.ToHsv();
66.271 + var hsv2 = c2.ToHsv();
66.272 + double dh = hsv1[0] - hsv2[0];
66.273 +
66.274 + // clamp to [-0.5,0.5]
66.275 + if (dh > 0.5)
66.276 + {
66.277 + dh -= 1.0;
66.278 + }
66.279 +
66.280 + if (dh < -0.5)
66.281 + {
66.282 + dh += 1.0;
66.283 + }
66.284 +
66.285 + double e = dh * dh;
66.286 + return Math.Sqrt(e);
66.287 + }
66.288 +
66.289 + /// <summary>
66.290 + /// Creates a color defined by an alpha value and another color.
66.291 + /// </summary>
66.292 + /// <param name="a">
66.293 + /// Alpha value.
66.294 + /// </param>
66.295 + /// <param name="color">
66.296 + /// The original color.
66.297 + /// </param>
66.298 + /// <returns>
66.299 + /// A color.
66.300 + /// </returns>
66.301 + public static OxyColor FromAColor(byte a, OxyColor color)
66.302 + {
66.303 + return new OxyColor { A = a, R = color.R, G = color.G, B = color.B };
66.304 + }
66.305 +
66.306 + /// <summary>
66.307 + /// Creates a color from the specified ARGB values.
66.308 + /// </summary>
66.309 + /// <param name="a">
66.310 + /// The alpha value.
66.311 + /// </param>
66.312 + /// <param name="r">
66.313 + /// The red value.
66.314 + /// </param>
66.315 + /// <param name="g">
66.316 + /// The green value.
66.317 + /// </param>
66.318 + /// <param name="b">
66.319 + /// The blue value.
66.320 + /// </param>
66.321 + /// <returns>
66.322 + /// A color.
66.323 + /// </returns>
66.324 + public static OxyColor FromArgb(byte a, byte r, byte g, byte b)
66.325 + {
66.326 + return new OxyColor { A = a, R = r, G = g, B = b };
66.327 + }
66.328 +
66.329 + /// <summary>
66.330 + /// Creates a new <see cref="OxyColor"/> structure from the specified RGB values.
66.331 + /// </summary>
66.332 + /// <param name="r">
66.333 + /// The red value.
66.334 + /// </param>
66.335 + /// <param name="g">
66.336 + /// The green value.
66.337 + /// </param>
66.338 + /// <param name="b">
66.339 + /// The blue value.
66.340 + /// </param>
66.341 + /// <returns>
66.342 + /// A <see cref="OxyColor"/> structure with the specified values and an alpha channel value of 1.
66.343 + /// </returns>
66.344 + public static OxyColor FromRgb(byte r, byte g, byte b)
66.345 + {
66.346 + // ReSharper restore InconsistentNaming
66.347 + return new OxyColor { A = 255, R = r, G = g, B = b };
66.348 + }
66.349 +
66.350 + /// <summary>
66.351 + /// Interpolates the specified colors.
66.352 + /// </summary>
66.353 + /// <param name="color1">
66.354 + /// The color1.
66.355 + /// </param>
66.356 + /// <param name="color2">
66.357 + /// The color2.
66.358 + /// </param>
66.359 + /// <param name="t">
66.360 + /// The t.
66.361 + /// </param>
66.362 + /// <returns>
66.363 + /// The interpolated color
66.364 + /// </returns>
66.365 + public static OxyColor Interpolate(OxyColor color1, OxyColor color2, double t)
66.366 + {
66.367 + double a = (color1.A * (1 - t)) + (color2.A * t);
66.368 + double r = (color1.R * (1 - t)) + (color2.R * t);
66.369 + double g = (color1.G * (1 - t)) + (color2.G * t);
66.370 + double b = (color1.B * (1 - t)) + (color2.B * t);
66.371 + return FromArgb((byte)a, (byte)r, (byte)g, (byte)b);
66.372 + }
66.373 +
66.374 + /// <summary>
66.375 + /// Convert OxyColor to double string.
66.376 + /// </summary>
66.377 + /// <returns>
66.378 + /// A OxyColor string, e.g. "255,200,180,50".
66.379 + /// </returns>
66.380 + public string ToByteString()
66.381 + {
66.382 + return string.Format(CultureInfo.InvariantCulture, "{0},{1},{2},{3}", this.A, this.R, this.G, this.B);
66.383 + }
66.384 +
66.385 + /// <summary>
66.386 + /// Determines whether the specified <see cref="System.Object"/> is equal to this instance.
66.387 + /// </summary>
66.388 + /// <param name="obj">
66.389 + /// The <see cref="System.Object"/> to compare with this instance.
66.390 + /// </param>
66.391 + /// <returns>
66.392 + /// <c>true</c> if the specified <see cref="System.Object"/> is equal to this instance; otherwise, <c>false</c> .
66.393 + /// </returns>
66.394 + public override bool Equals(object obj)
66.395 + {
66.396 + if (ReferenceEquals(null, obj))
66.397 + {
66.398 + return false;
66.399 + }
66.400 +
66.401 + if (ReferenceEquals(this, obj))
66.402 + {
66.403 + return true;
66.404 + }
66.405 +
66.406 + if (obj.GetType() != typeof(OxyColor))
66.407 + {
66.408 + return false;
66.409 + }
66.410 +
66.411 + return this.Equals((OxyColor)obj);
66.412 + }
66.413 +
66.414 + /// <summary>
66.415 + /// Determines whether the specified <see cref="OxyColor"/> is equal to this instance.
66.416 + /// </summary>
66.417 + /// <param name="other">
66.418 + /// The <see cref="OxyColor"/> to compare with this instance.
66.419 + /// </param>
66.420 + /// <returns>
66.421 + /// <c>true</c> if the specified <see cref="OxyColor"/> is equal to this instance; otherwise, <c>false</c> .
66.422 + /// </returns>
66.423 + public bool Equals(OxyColor other)
66.424 + {
66.425 + if (ReferenceEquals(null, other))
66.426 + {
66.427 + return false;
66.428 + }
66.429 +
66.430 + if (ReferenceEquals(this, other))
66.431 + {
66.432 + return true;
66.433 + }
66.434 +
66.435 + return other.A == this.A && other.R == this.R && other.G == this.G && other.B == this.B;
66.436 + }
66.437 +
66.438 + /// <summary>
66.439 + /// Gets the color name.
66.440 + /// </summary>
66.441 + /// <returns>
66.442 + /// The color name.
66.443 + /// </returns>
66.444 + public string GetColorName()
66.445 + {
66.446 + var t = typeof(OxyColors);
66.447 + var colors = t.GetFields(BindingFlags.Public | BindingFlags.Static);
66.448 + var colorField = colors.FirstOrDefault(
66.449 + field =>
66.450 + {
66.451 + var color = field.GetValue(null);
66.452 + return this.Equals(color);
66.453 + });
66.454 + return colorField != null ? colorField.Name : null;
66.455 + }
66.456 +
66.457 + /// <summary>
66.458 + /// Returns a hash code for this instance.
66.459 + /// </summary>
66.460 + /// <returns>
66.461 + /// A hash code for this instance, suitable for use in hashing algorithms and data structures like a hash table.
66.462 + /// </returns>
66.463 + public override int GetHashCode()
66.464 + {
66.465 + unchecked
66.466 + {
66.467 + int result = this.A.GetHashCode();
66.468 + result = (result * 397) ^ this.R.GetHashCode();
66.469 + result = (result * 397) ^ this.G.GetHashCode();
66.470 + result = (result * 397) ^ this.B.GetHashCode();
66.471 + return result;
66.472 + }
66.473 + }
66.474 +
66.475 + /// <summary>
66.476 + /// Returns a <see cref="System.String"/> that represents this instance.
66.477 + /// </summary>
66.478 + /// <returns>
66.479 + /// A <see cref="System.String"/> that represents this instance.
66.480 + /// </returns>
66.481 + public override string ToString()
66.482 + {
66.483 + return string.Format(
66.484 + CultureInfo.InvariantCulture, "#{0:x2}{1:x2}{2:x2}{3:x2}", this.A, this.R, this.G, this.B);
66.485 + }
66.486 +
66.487 + /// <summary>
66.488 + /// Changes the opacity value.
66.489 + /// </summary>
66.490 + /// <param name="newAlpha">
66.491 + /// The new alpha.
66.492 + /// </param>
66.493 + /// <returns>
66.494 + /// The new color.
66.495 + /// </returns>
66.496 + public OxyColor ChangeAlpha(byte newAlpha)
66.497 + {
66.498 + return FromArgb(newAlpha, this.R, this.G, this.B);
66.499 + }
66.500 +
66.501 + /// <summary>
66.502 + /// Calculates the complementary OxyColor.
66.503 + /// </summary>
66.504 + /// <returns>
66.505 + /// The complementary OxyColor.
66.506 + /// </returns>
66.507 + public OxyColor Complementary()
66.508 + {
66.509 + // http://en.wikipedia.org/wiki/Complementary_Color
66.510 + var hsv = this.ToHsv();
66.511 + double newHue = hsv[0] - 0.5;
66.512 +
66.513 + // clamp to [0,1]
66.514 + if (newHue < 0)
66.515 + {
66.516 + newHue += 1.0;
66.517 + }
66.518 +
66.519 + return FromHsv(newHue, hsv[1], hsv[2]);
66.520 + }
66.521 +
66.522 + /// <summary>
66.523 + /// Converts from a <see cref="OxyColor"/> to HSV values (double)
66.524 + /// </summary>
66.525 + /// <returns>
66.526 + /// Array of [Hue,Saturation,Value] in the range [0,1]
66.527 + /// </returns>
66.528 + public double[] ToHsv()
66.529 + {
66.530 + byte r = this.R;
66.531 + byte g = this.G;
66.532 + byte b = this.B;
66.533 +
66.534 + byte min = Math.Min(Math.Min(r, g), b);
66.535 + byte v = Math.Max(Math.Max(r, g), b);
66.536 + double delta = v - min;
66.537 +
66.538 + double s = v.Equals(0) ? 0 : delta / v;
66.539 + double h = 0;
66.540 +
66.541 + if (s.Equals(0))
66.542 + {
66.543 + h = 0.0;
66.544 + }
66.545 + else
66.546 + {
66.547 + if (r == v)
66.548 + {
66.549 + h = (g - b) / delta;
66.550 + }
66.551 + else if (g == v)
66.552 + {
66.553 + h = 2 + ((b - r) / delta);
66.554 + }
66.555 + else if (b == v)
66.556 + {
66.557 + h = 4 + ((r - g) / delta);
66.558 + }
66.559 +
66.560 + h *= 60;
66.561 + if (h < 0.0)
66.562 + {
66.563 + h += 360;
66.564 + }
66.565 + }
66.566 +
66.567 + var hsv = new double[3];
66.568 + hsv[0] = h / 360.0;
66.569 + hsv[1] = s;
66.570 + hsv[2] = v / 255.0;
66.571 + return hsv;
66.572 + }
66.573 +
66.574 + /// <summary>
66.575 + /// Changes the intensity.
66.576 + /// </summary>
66.577 + /// <param name="factor">
66.578 + /// The factor.
66.579 + /// </param>
66.580 + /// <returns>
66.581 + /// The new OxyColor.
66.582 + /// </returns>
66.583 + public OxyColor ChangeIntensity(double factor)
66.584 + {
66.585 + var hsv = this.ToHsv();
66.586 + hsv[2] *= factor;
66.587 + if (hsv[2] > 1.0)
66.588 + {
66.589 + hsv[2] = 1.0;
66.590 + }
66.591 +
66.592 + return FromHsv(hsv);
66.593 + }
66.594 +
66.595 + /// <summary>
66.596 + /// Converts to an unsigned integer.
66.597 + /// </summary>
66.598 + /// <returns>
66.599 + /// The <see cref="uint"/>.
66.600 + /// </returns>
66.601 + public uint ToUint()
66.602 + {
66.603 + uint u = (uint)this.A << 24;
66.604 + u += (uint)this.R << 16;
66.605 + u += (uint)this.G << 8;
66.606 + u += this.B;
66.607 + return u;
66.608 +
66.609 + // (UInt32)((UInt32)c.A << 24 + (UInt32)c.R << 16 + (UInt32)c.G << 8 + (UInt32)c.B);
66.610 + }
66.611 +
66.612 + /// <summary>
66.613 + /// Returns C# code that generates this instance.
66.614 + /// </summary>
66.615 + /// <returns>
66.616 + /// The to code.
66.617 + /// </returns>
66.618 + public string ToCode()
66.619 + {
66.620 + string name = this.GetColorName();
66.621 + if (name != null)
66.622 + {
66.623 + return string.Format("OxyColors.{0}", name);
66.624 + }
66.625 +
66.626 + return string.Format("OxyColor.FromArgb({0}, {1}, {2}, {3})", this.A, this.R, this.G, this.B);
66.627 + }
66.628 + }
66.629 +}
66.630 \ No newline at end of file
67.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
67.2 +++ b/External/OxyPlot/OxyPlot/Foundation/OxyColorConverter.cs Sat Jun 08 16:53:22 2013 +0000
67.3 @@ -0,0 +1,135 @@
67.4 +// --------------------------------------------------------------------------------------------------------------------
67.5 +// <copyright file="OxyColorConverter.cs" company="OxyPlot">
67.6 +// The MIT License (MIT)
67.7 +//
67.8 +// Copyright (c) 2012 Oystein Bjorke
67.9 +//
67.10 +// Permission is hereby granted, free of charge, to any person obtaining a
67.11 +// copy of this software and associated documentation files (the
67.12 +// "Software"), to deal in the Software without restriction, including
67.13 +// without limitation the rights to use, copy, modify, merge, publish,
67.14 +// distribute, sublicense, and/or sell copies of the Software, and to
67.15 +// permit persons to whom the Software is furnished to do so, subject to
67.16 +// the following conditions:
67.17 +//
67.18 +// The above copyright notice and this permission notice shall be included
67.19 +// in all copies or substantial portions of the Software.
67.20 +//
67.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
67.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
67.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
67.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
67.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
67.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
67.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
67.28 +// </copyright>
67.29 +// <summary>
67.30 +// Converts colors from one data type to another. Access this class through the TypeDescriptor.
67.31 +// </summary>
67.32 +// --------------------------------------------------------------------------------------------------------------------
67.33 +namespace OxyPlot
67.34 +{
67.35 + using System;
67.36 + using System.ComponentModel;
67.37 + using System.Globalization;
67.38 +
67.39 + /// <summary>
67.40 + /// Converts between <see cref="OxyColor"/> and <see cref="System.String"/>. Access this class through the TypeDescriptor.
67.41 + /// </summary>
67.42 + public class OxyColorConverter : TypeConverter
67.43 + {
67.44 + /// <summary>
67.45 + /// Determines whether an object can be converted from a given type to an instance of a <see cref="OxyColor"/>.
67.46 + /// </summary>
67.47 + /// <param name="context">
67.48 + /// Describes the context information of a type.
67.49 + /// </param>
67.50 + /// <param name="sourceType">
67.51 + /// The type of the source that is being evaluated for conversion.
67.52 + /// </param>
67.53 + /// <returns>
67.54 + /// True if the type can be converted to a <see cref="OxyColor"/>; otherwise, false.
67.55 + /// </returns>
67.56 + public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType)
67.57 + {
67.58 + return (sourceType == typeof(string)) || base.CanConvertFrom(context, sourceType);
67.59 + }
67.60 +
67.61 + /// <summary>
67.62 + /// Determines whether an instance of a <see cref="OxyColor"/> can be converted to a different type.
67.63 + /// </summary>
67.64 + /// <param name="context">
67.65 + /// Describes the context information of a type.
67.66 + /// </param>
67.67 + /// <param name="destinationType">
67.68 + /// The desired type this <see cref="OxyColor"/> is being evaluated for conversion.
67.69 + /// </param>
67.70 + /// <returns>
67.71 + /// True if this <see cref="OxyColor"/> can be converted to destinationType; otherwise, false.
67.72 + /// </returns>
67.73 + public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType)
67.74 + {
67.75 + return (destinationType == typeof(string)) || base.CanConvertTo(context, destinationType);
67.76 + }
67.77 +
67.78 + /// <summary>
67.79 + /// Attempts to convert the specified object to a <see cref="OxyColor"/>.
67.80 + /// </summary>
67.81 + /// <param name="context">
67.82 + /// Describes the context information of a type.
67.83 + /// </param>
67.84 + /// <param name="culture">
67.85 + /// Cultural information to respect during conversion.
67.86 + /// </param>
67.87 + /// <param name="value">
67.88 + /// The object being converted.
67.89 + /// </param>
67.90 + /// <returns>
67.91 + /// The <see cref="OxyColor"/> created from converting value.
67.92 + /// </returns>
67.93 + public override object ConvertFrom(ITypeDescriptorContext context, CultureInfo culture, object value)
67.94 + {
67.95 + var str = value as string;
67.96 + if (str == null)
67.97 + {
67.98 + return base.ConvertFrom(context, culture, value);
67.99 + }
67.100 +
67.101 + return OxyColor.Parse(str);
67.102 + }
67.103 +
67.104 + /// <summary>
67.105 + /// Attempts to convert a <see cref="OxyColor"/> to a specified type.
67.106 + /// </summary>
67.107 + /// <param name="context">
67.108 + /// Describes the context information of a type.
67.109 + /// </param>
67.110 + /// <param name="culture">
67.111 + /// Describes the <see cref="CultureInfo"/> of the type being converted.
67.112 + /// </param>
67.113 + /// <param name="value">
67.114 + /// The <see cref="OxyColor"/> to convert.
67.115 + /// </param>
67.116 + /// <param name="destinationType">
67.117 + /// The type to convert this <see cref="OxyColor"/> to.
67.118 + /// </param>
67.119 + /// <returns>
67.120 + /// The object created from converting this <see cref="OxyColor"/>.
67.121 + /// </returns>
67.122 + public override object ConvertTo(
67.123 + ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType)
67.124 + {
67.125 + if (destinationType == null)
67.126 + {
67.127 + throw new ArgumentNullException("destinationType");
67.128 + }
67.129 +
67.130 + if (destinationType == typeof(string))
67.131 + {
67.132 + return value != null ? value.ToString() : null;
67.133 + }
67.134 +
67.135 + return base.ConvertTo(context, culture, value, destinationType);
67.136 + }
67.137 + }
67.138 +}
67.139 \ No newline at end of file
68.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
68.2 +++ b/External/OxyPlot/OxyPlot/Foundation/OxyColors.cs Sat Jun 08 16:53:22 2013 +0000
68.3 @@ -0,0 +1,743 @@
68.4 +// --------------------------------------------------------------------------------------------------------------------
68.5 +// <copyright file="OxyColors.cs" company="OxyPlot">
68.6 +// The MIT License (MIT)
68.7 +//
68.8 +// Copyright (c) 2012 Oystein Bjorke
68.9 +//
68.10 +// Permission is hereby granted, free of charge, to any person obtaining a
68.11 +// copy of this software and associated documentation files (the
68.12 +// "Software"), to deal in the Software without restriction, including
68.13 +// without limitation the rights to use, copy, modify, merge, publish,
68.14 +// distribute, sublicense, and/or sell copies of the Software, and to
68.15 +// permit persons to whom the Software is furnished to do so, subject to
68.16 +// the following conditions:
68.17 +//
68.18 +// The above copyright notice and this permission notice shall be included
68.19 +// in all copies or substantial portions of the Software.
68.20 +//
68.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
68.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
68.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
68.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
68.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
68.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
68.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
68.28 +// </copyright>
68.29 +// <summary>
68.30 +// Implements a set of predefined colors.
68.31 +// </summary>
68.32 +// --------------------------------------------------------------------------------------------------------------------
68.33 +namespace OxyPlot
68.34 +{
68.35 + /// <summary>
68.36 + /// Implements a set of predefined colors.
68.37 + /// </summary>
68.38 + public static class OxyColors
68.39 + {
68.40 + /// <summary>
68.41 + /// The alice blue.
68.42 + /// </summary>
68.43 + public static readonly OxyColor AliceBlue = OxyColor.FromUInt32(0xFFF0F8FF);
68.44 +
68.45 + /// <summary>
68.46 + /// The antique white.
68.47 + /// </summary>
68.48 + public static readonly OxyColor AntiqueWhite = OxyColor.FromUInt32(0xFFFAEBD7);
68.49 +
68.50 + /// <summary>
68.51 + /// The aqua.
68.52 + /// </summary>
68.53 + public static readonly OxyColor Aqua = OxyColor.FromUInt32(0xFF00FFFF);
68.54 +
68.55 + /// <summary>
68.56 + /// The aquamarine.
68.57 + /// </summary>
68.58 + public static readonly OxyColor Aquamarine = OxyColor.FromUInt32(0xFF7FFFD4);
68.59 +
68.60 + /// <summary>
68.61 + /// The azure.
68.62 + /// </summary>
68.63 + public static readonly OxyColor Azure = OxyColor.FromUInt32(0xFFF0FFFF);
68.64 +
68.65 + /// <summary>
68.66 + /// The beige.
68.67 + /// </summary>
68.68 + public static readonly OxyColor Beige = OxyColor.FromUInt32(0xFFF5F5DC);
68.69 +
68.70 + /// <summary>
68.71 + /// The bisque.
68.72 + /// </summary>
68.73 + public static readonly OxyColor Bisque = OxyColor.FromUInt32(0xFFFFE4C4);
68.74 +
68.75 + /// <summary>
68.76 + /// The black.
68.77 + /// </summary>
68.78 + public static readonly OxyColor Black = OxyColor.FromUInt32(0xFF000000);
68.79 +
68.80 + /// <summary>
68.81 + /// The blanched almond.
68.82 + /// </summary>
68.83 + public static readonly OxyColor BlanchedAlmond = OxyColor.FromUInt32(0xFFFFEBCD);
68.84 +
68.85 + /// <summary>
68.86 + /// The blue.
68.87 + /// </summary>
68.88 + public static readonly OxyColor Blue = OxyColor.FromUInt32(0xFF0000FF);
68.89 +
68.90 + /// <summary>
68.91 + /// The blue violet.
68.92 + /// </summary>
68.93 + public static readonly OxyColor BlueViolet = OxyColor.FromUInt32(0xFF8A2BE2);
68.94 +
68.95 + /// <summary>
68.96 + /// The brown.
68.97 + /// </summary>
68.98 + public static readonly OxyColor Brown = OxyColor.FromUInt32(0xFFA52A2A);
68.99 +
68.100 + /// <summary>
68.101 + /// The burly wood.
68.102 + /// </summary>
68.103 + public static readonly OxyColor BurlyWood = OxyColor.FromUInt32(0xFFDEB887);
68.104 +
68.105 + /// <summary>
68.106 + /// The cadet blue.
68.107 + /// </summary>
68.108 + public static readonly OxyColor CadetBlue = OxyColor.FromUInt32(0xFF5F9EA0);
68.109 +
68.110 + /// <summary>
68.111 + /// The chartreuse.
68.112 + /// </summary>
68.113 + public static readonly OxyColor Chartreuse = OxyColor.FromUInt32(0xFF7FFF00);
68.114 +
68.115 + /// <summary>
68.116 + /// The chocolate.
68.117 + /// </summary>
68.118 + public static readonly OxyColor Chocolate = OxyColor.FromUInt32(0xFFD2691E);
68.119 +
68.120 + /// <summary>
68.121 + /// The coral.
68.122 + /// </summary>
68.123 + public static readonly OxyColor Coral = OxyColor.FromUInt32(0xFFFF7F50);
68.124 +
68.125 + /// <summary>
68.126 + /// The cornflower blue.
68.127 + /// </summary>
68.128 + public static readonly OxyColor CornflowerBlue = OxyColor.FromUInt32(0xFF6495ED);
68.129 +
68.130 + /// <summary>
68.131 + /// The cornsilk.
68.132 + /// </summary>
68.133 + public static readonly OxyColor Cornsilk = OxyColor.FromUInt32(0xFFFFF8DC);
68.134 +
68.135 + /// <summary>
68.136 + /// The crimson.
68.137 + /// </summary>
68.138 + public static readonly OxyColor Crimson = OxyColor.FromUInt32(0xFFDC143C);
68.139 +
68.140 + /// <summary>
68.141 + /// The cyan.
68.142 + /// </summary>
68.143 + public static readonly OxyColor Cyan = OxyColor.FromUInt32(0xFF00FFFF);
68.144 +
68.145 + /// <summary>
68.146 + /// The dark blue.
68.147 + /// </summary>
68.148 + public static readonly OxyColor DarkBlue = OxyColor.FromUInt32(0xFF00008B);
68.149 +
68.150 + /// <summary>
68.151 + /// The dark cyan.
68.152 + /// </summary>
68.153 + public static readonly OxyColor DarkCyan = OxyColor.FromUInt32(0xFF008B8B);
68.154 +
68.155 + /// <summary>
68.156 + /// The dark goldenrod.
68.157 + /// </summary>
68.158 + public static readonly OxyColor DarkGoldenrod = OxyColor.FromUInt32(0xFFB8860B);
68.159 +
68.160 + /// <summary>
68.161 + /// The dark gray.
68.162 + /// </summary>
68.163 + public static readonly OxyColor DarkGray = OxyColor.FromUInt32(0xFFA9A9A9);
68.164 +
68.165 + /// <summary>
68.166 + /// The dark green.
68.167 + /// </summary>
68.168 + public static readonly OxyColor DarkGreen = OxyColor.FromUInt32(0xFF006400);
68.169 +
68.170 + /// <summary>
68.171 + /// The dark khaki.
68.172 + /// </summary>
68.173 + public static readonly OxyColor DarkKhaki = OxyColor.FromUInt32(0xFFBDB76B);
68.174 +
68.175 + /// <summary>
68.176 + /// The dark magenta.
68.177 + /// </summary>
68.178 + public static readonly OxyColor DarkMagenta = OxyColor.FromUInt32(0xFF8B008B);
68.179 +
68.180 + /// <summary>
68.181 + /// The dark olive green.
68.182 + /// </summary>
68.183 + public static readonly OxyColor DarkOliveGreen = OxyColor.FromUInt32(0xFF556B2F);
68.184 +
68.185 + /// <summary>
68.186 + /// The dark orange.
68.187 + /// </summary>
68.188 + public static readonly OxyColor DarkOrange = OxyColor.FromUInt32(0xFFFF8C00);
68.189 +
68.190 + /// <summary>
68.191 + /// The dark orchid.
68.192 + /// </summary>
68.193 + public static readonly OxyColor DarkOrchid = OxyColor.FromUInt32(0xFF9932CC);
68.194 +
68.195 + /// <summary>
68.196 + /// The dark red.
68.197 + /// </summary>
68.198 + public static readonly OxyColor DarkRed = OxyColor.FromUInt32(0xFF8B0000);
68.199 +
68.200 + /// <summary>
68.201 + /// The dark salmon.
68.202 + /// </summary>
68.203 + public static readonly OxyColor DarkSalmon = OxyColor.FromUInt32(0xFFE9967A);
68.204 +
68.205 + /// <summary>
68.206 + /// The dark sea green.
68.207 + /// </summary>
68.208 + public static readonly OxyColor DarkSeaGreen = OxyColor.FromUInt32(0xFF8FBC8F);
68.209 +
68.210 + /// <summary>
68.211 + /// The dark slate blue.
68.212 + /// </summary>
68.213 + public static readonly OxyColor DarkSlateBlue = OxyColor.FromUInt32(0xFF483D8B);
68.214 +
68.215 + /// <summary>
68.216 + /// The dark slate gray.
68.217 + /// </summary>
68.218 + public static readonly OxyColor DarkSlateGray = OxyColor.FromUInt32(0xFF2F4F4F);
68.219 +
68.220 + /// <summary>
68.221 + /// The dark turquoise.
68.222 + /// </summary>
68.223 + public static readonly OxyColor DarkTurquoise = OxyColor.FromUInt32(0xFF00CED1);
68.224 +
68.225 + /// <summary>
68.226 + /// The dark violet.
68.227 + /// </summary>
68.228 + public static readonly OxyColor DarkViolet = OxyColor.FromUInt32(0xFF9400D3);
68.229 +
68.230 + /// <summary>
68.231 + /// The deep pink.
68.232 + /// </summary>
68.233 + public static readonly OxyColor DeepPink = OxyColor.FromUInt32(0xFFFF1493);
68.234 +
68.235 + /// <summary>
68.236 + /// The deep sky blue.
68.237 + /// </summary>
68.238 + public static readonly OxyColor DeepSkyBlue = OxyColor.FromUInt32(0xFF00BFFF);
68.239 +
68.240 + /// <summary>
68.241 + /// The dim gray.
68.242 + /// </summary>
68.243 + public static readonly OxyColor DimGray = OxyColor.FromUInt32(0xFF696969);
68.244 +
68.245 + /// <summary>
68.246 + /// The dodger blue.
68.247 + /// </summary>
68.248 + public static readonly OxyColor DodgerBlue = OxyColor.FromUInt32(0xFF1E90FF);
68.249 +
68.250 + /// <summary>
68.251 + /// The firebrick.
68.252 + /// </summary>
68.253 + public static readonly OxyColor Firebrick = OxyColor.FromUInt32(0xFFB22222);
68.254 +
68.255 + /// <summary>
68.256 + /// The floral white.
68.257 + /// </summary>
68.258 + public static readonly OxyColor FloralWhite = OxyColor.FromUInt32(0xFFFFFAF0);
68.259 +
68.260 + /// <summary>
68.261 + /// The forest green.
68.262 + /// </summary>
68.263 + public static readonly OxyColor ForestGreen = OxyColor.FromUInt32(0xFF228B22);
68.264 +
68.265 + /// <summary>
68.266 + /// The fuchsia.
68.267 + /// </summary>
68.268 + public static readonly OxyColor Fuchsia = OxyColor.FromUInt32(0xFFFF00FF);
68.269 +
68.270 + /// <summary>
68.271 + /// The gainsboro.
68.272 + /// </summary>
68.273 + public static readonly OxyColor Gainsboro = OxyColor.FromUInt32(0xFFDCDCDC);
68.274 +
68.275 + /// <summary>
68.276 + /// The ghost white.
68.277 + /// </summary>
68.278 + public static readonly OxyColor GhostWhite = OxyColor.FromUInt32(0xFFF8F8FF);
68.279 +
68.280 + /// <summary>
68.281 + /// The gold.
68.282 + /// </summary>
68.283 + public static readonly OxyColor Gold = OxyColor.FromUInt32(0xFFFFD700);
68.284 +
68.285 + /// <summary>
68.286 + /// The goldenrod.
68.287 + /// </summary>
68.288 + public static readonly OxyColor Goldenrod = OxyColor.FromUInt32(0xFFDAA520);
68.289 +
68.290 + /// <summary>
68.291 + /// The gray.
68.292 + /// </summary>
68.293 + public static readonly OxyColor Gray = OxyColor.FromUInt32(0xFF808080);
68.294 +
68.295 + /// <summary>
68.296 + /// The green.
68.297 + /// </summary>
68.298 + public static readonly OxyColor Green = OxyColor.FromUInt32(0xFF008000);
68.299 +
68.300 + /// <summary>
68.301 + /// The green yellow.
68.302 + /// </summary>
68.303 + public static readonly OxyColor GreenYellow = OxyColor.FromUInt32(0xFFADFF2F);
68.304 +
68.305 + /// <summary>
68.306 + /// The honeydew.
68.307 + /// </summary>
68.308 + public static readonly OxyColor Honeydew = OxyColor.FromUInt32(0xFFF0FFF0);
68.309 +
68.310 + /// <summary>
68.311 + /// The hot pink.
68.312 + /// </summary>
68.313 + public static readonly OxyColor HotPink = OxyColor.FromUInt32(0xFFFF69B4);
68.314 +
68.315 + /// <summary>
68.316 + /// The indian red.
68.317 + /// </summary>
68.318 + public static readonly OxyColor IndianRed = OxyColor.FromUInt32(0xFFCD5C5C);
68.319 +
68.320 + /// <summary>
68.321 + /// The indigo.
68.322 + /// </summary>
68.323 + public static readonly OxyColor Indigo = OxyColor.FromUInt32(0xFF4B0082);
68.324 +
68.325 + /// <summary>
68.326 + /// The ivory.
68.327 + /// </summary>
68.328 + public static readonly OxyColor Ivory = OxyColor.FromUInt32(0xFFFFFFF0);
68.329 +
68.330 + /// <summary>
68.331 + /// The khaki.
68.332 + /// </summary>
68.333 + public static readonly OxyColor Khaki = OxyColor.FromUInt32(0xFFF0E68C);
68.334 +
68.335 + /// <summary>
68.336 + /// The lavender.
68.337 + /// </summary>
68.338 + public static readonly OxyColor Lavender = OxyColor.FromUInt32(0xFFE6E6FA);
68.339 +
68.340 + /// <summary>
68.341 + /// The lavender blush.
68.342 + /// </summary>
68.343 + public static readonly OxyColor LavenderBlush = OxyColor.FromUInt32(0xFFFFF0F5);
68.344 +
68.345 + /// <summary>
68.346 + /// The lawn green.
68.347 + /// </summary>
68.348 + public static readonly OxyColor LawnGreen = OxyColor.FromUInt32(0xFF7CFC00);
68.349 +
68.350 + /// <summary>
68.351 + /// The lemon chiffon.
68.352 + /// </summary>
68.353 + public static readonly OxyColor LemonChiffon = OxyColor.FromUInt32(0xFFFFFACD);
68.354 +
68.355 + /// <summary>
68.356 + /// The light blue.
68.357 + /// </summary>
68.358 + public static readonly OxyColor LightBlue = OxyColor.FromUInt32(0xFFADD8E6);
68.359 +
68.360 + /// <summary>
68.361 + /// The light coral.
68.362 + /// </summary>
68.363 + public static readonly OxyColor LightCoral = OxyColor.FromUInt32(0xFFF08080);
68.364 +
68.365 + /// <summary>
68.366 + /// The light cyan.
68.367 + /// </summary>
68.368 + public static readonly OxyColor LightCyan = OxyColor.FromUInt32(0xFFE0FFFF);
68.369 +
68.370 + /// <summary>
68.371 + /// The light goldenrod yellow.
68.372 + /// </summary>
68.373 + public static readonly OxyColor LightGoldenrodYellow = OxyColor.FromUInt32(0xFFFAFAD2);
68.374 +
68.375 + /// <summary>
68.376 + /// The light gray.
68.377 + /// </summary>
68.378 + public static readonly OxyColor LightGray = OxyColor.FromUInt32(0xFFD3D3D3);
68.379 +
68.380 + /// <summary>
68.381 + /// The light green.
68.382 + /// </summary>
68.383 + public static readonly OxyColor LightGreen = OxyColor.FromUInt32(0xFF90EE90);
68.384 +
68.385 + /// <summary>
68.386 + /// The light pink.
68.387 + /// </summary>
68.388 + public static readonly OxyColor LightPink = OxyColor.FromUInt32(0xFFFFB6C1);
68.389 +
68.390 + /// <summary>
68.391 + /// The light salmon.
68.392 + /// </summary>
68.393 + public static readonly OxyColor LightSalmon = OxyColor.FromUInt32(0xFFFFA07A);
68.394 +
68.395 + /// <summary>
68.396 + /// The light sea green.
68.397 + /// </summary>
68.398 + public static readonly OxyColor LightSeaGreen = OxyColor.FromUInt32(0xFF20B2AA);
68.399 +
68.400 + /// <summary>
68.401 + /// The light sky blue.
68.402 + /// </summary>
68.403 + public static readonly OxyColor LightSkyBlue = OxyColor.FromUInt32(0xFF87CEFA);
68.404 +
68.405 + /// <summary>
68.406 + /// The light slate gray.
68.407 + /// </summary>
68.408 + public static readonly OxyColor LightSlateGray = OxyColor.FromUInt32(0xFF778899);
68.409 +
68.410 + /// <summary>
68.411 + /// The light steel blue.
68.412 + /// </summary>
68.413 + public static readonly OxyColor LightSteelBlue = OxyColor.FromUInt32(0xFFB0C4DE);
68.414 +
68.415 + /// <summary>
68.416 + /// The light yellow.
68.417 + /// </summary>
68.418 + public static readonly OxyColor LightYellow = OxyColor.FromUInt32(0xFFFFFFE0);
68.419 +
68.420 + /// <summary>
68.421 + /// The lime.
68.422 + /// </summary>
68.423 + public static readonly OxyColor Lime = OxyColor.FromUInt32(0xFF00FF00);
68.424 +
68.425 + /// <summary>
68.426 + /// The lime green.
68.427 + /// </summary>
68.428 + public static readonly OxyColor LimeGreen = OxyColor.FromUInt32(0xFF32CD32);
68.429 +
68.430 + /// <summary>
68.431 + /// The linen.
68.432 + /// </summary>
68.433 + public static readonly OxyColor Linen = OxyColor.FromUInt32(0xFFFAF0E6);
68.434 +
68.435 + /// <summary>
68.436 + /// The magenta.
68.437 + /// </summary>
68.438 + public static readonly OxyColor Magenta = OxyColor.FromUInt32(0xFFFF00FF);
68.439 +
68.440 + /// <summary>
68.441 + /// The maroon.
68.442 + /// </summary>
68.443 + public static readonly OxyColor Maroon = OxyColor.FromUInt32(0xFF800000);
68.444 +
68.445 + /// <summary>
68.446 + /// The medium aquamarine.
68.447 + /// </summary>
68.448 + public static readonly OxyColor MediumAquamarine = OxyColor.FromUInt32(0xFF66CDAA);
68.449 +
68.450 + /// <summary>
68.451 + /// The medium blue.
68.452 + /// </summary>
68.453 + public static readonly OxyColor MediumBlue = OxyColor.FromUInt32(0xFF0000CD);
68.454 +
68.455 + /// <summary>
68.456 + /// The medium orchid.
68.457 + /// </summary>
68.458 + public static readonly OxyColor MediumOrchid = OxyColor.FromUInt32(0xFFBA55D3);
68.459 +
68.460 + /// <summary>
68.461 + /// The medium purple.
68.462 + /// </summary>
68.463 + public static readonly OxyColor MediumPurple = OxyColor.FromUInt32(0xFF9370DB);
68.464 +
68.465 + /// <summary>
68.466 + /// The medium sea green.
68.467 + /// </summary>
68.468 + public static readonly OxyColor MediumSeaGreen = OxyColor.FromUInt32(0xFF3CB371);
68.469 +
68.470 + /// <summary>
68.471 + /// The medium slate blue.
68.472 + /// </summary>
68.473 + public static readonly OxyColor MediumSlateBlue = OxyColor.FromUInt32(0xFF7B68EE);
68.474 +
68.475 + /// <summary>
68.476 + /// The medium spring green.
68.477 + /// </summary>
68.478 + public static readonly OxyColor MediumSpringGreen = OxyColor.FromUInt32(0xFF00FA9A);
68.479 +
68.480 + /// <summary>
68.481 + /// The medium turquoise.
68.482 + /// </summary>
68.483 + public static readonly OxyColor MediumTurquoise = OxyColor.FromUInt32(0xFF48D1CC);
68.484 +
68.485 + /// <summary>
68.486 + /// The medium violet red.
68.487 + /// </summary>
68.488 + public static readonly OxyColor MediumVioletRed = OxyColor.FromUInt32(0xFFC71585);
68.489 +
68.490 + /// <summary>
68.491 + /// The midnight blue.
68.492 + /// </summary>
68.493 + public static readonly OxyColor MidnightBlue = OxyColor.FromUInt32(0xFF191970);
68.494 +
68.495 + /// <summary>
68.496 + /// The mint cream.
68.497 + /// </summary>
68.498 + public static readonly OxyColor MintCream = OxyColor.FromUInt32(0xFFF5FFFA);
68.499 +
68.500 + /// <summary>
68.501 + /// The misty rose.
68.502 + /// </summary>
68.503 + public static readonly OxyColor MistyRose = OxyColor.FromUInt32(0xFFFFE4E1);
68.504 +
68.505 + /// <summary>
68.506 + /// The moccasin.
68.507 + /// </summary>
68.508 + public static readonly OxyColor Moccasin = OxyColor.FromUInt32(0xFFFFE4B5);
68.509 +
68.510 + /// <summary>
68.511 + /// The navajo white.
68.512 + /// </summary>
68.513 + public static readonly OxyColor NavajoWhite = OxyColor.FromUInt32(0xFFFFDEAD);
68.514 +
68.515 + /// <summary>
68.516 + /// The navy.
68.517 + /// </summary>
68.518 + public static readonly OxyColor Navy = OxyColor.FromUInt32(0xFF000080);
68.519 +
68.520 + /// <summary>
68.521 + /// The old lace.
68.522 + /// </summary>
68.523 + public static readonly OxyColor OldLace = OxyColor.FromUInt32(0xFFFDF5E6);
68.524 +
68.525 + /// <summary>
68.526 + /// The olive.
68.527 + /// </summary>
68.528 + public static readonly OxyColor Olive = OxyColor.FromUInt32(0xFF808000);
68.529 +
68.530 + /// <summary>
68.531 + /// The olive drab.
68.532 + /// </summary>
68.533 + public static readonly OxyColor OliveDrab = OxyColor.FromUInt32(0xFF6B8E23);
68.534 +
68.535 + /// <summary>
68.536 + /// The orange.
68.537 + /// </summary>
68.538 + public static readonly OxyColor Orange = OxyColor.FromUInt32(0xFFFFA500);
68.539 +
68.540 + /// <summary>
68.541 + /// The orange red.
68.542 + /// </summary>
68.543 + public static readonly OxyColor OrangeRed = OxyColor.FromUInt32(0xFFFF4500);
68.544 +
68.545 + /// <summary>
68.546 + /// The orchid.
68.547 + /// </summary>
68.548 + public static readonly OxyColor Orchid = OxyColor.FromUInt32(0xFFDA70D6);
68.549 +
68.550 + /// <summary>
68.551 + /// The pale goldenrod.
68.552 + /// </summary>
68.553 + public static readonly OxyColor PaleGoldenrod = OxyColor.FromUInt32(0xFFEEE8AA);
68.554 +
68.555 + /// <summary>
68.556 + /// The pale green.
68.557 + /// </summary>
68.558 + public static readonly OxyColor PaleGreen = OxyColor.FromUInt32(0xFF98FB98);
68.559 +
68.560 + /// <summary>
68.561 + /// The pale turquoise.
68.562 + /// </summary>
68.563 + public static readonly OxyColor PaleTurquoise = OxyColor.FromUInt32(0xFFAFEEEE);
68.564 +
68.565 + /// <summary>
68.566 + /// The pale violet red.
68.567 + /// </summary>
68.568 + public static readonly OxyColor PaleVioletRed = OxyColor.FromUInt32(0xFFDB7093);
68.569 +
68.570 + /// <summary>
68.571 + /// The papaya whip.
68.572 + /// </summary>
68.573 + public static readonly OxyColor PapayaWhip = OxyColor.FromUInt32(0xFFFFEFD5);
68.574 +
68.575 + /// <summary>
68.576 + /// The peach puff.
68.577 + /// </summary>
68.578 + public static readonly OxyColor PeachPuff = OxyColor.FromUInt32(0xFFFFDAB9);
68.579 +
68.580 + /// <summary>
68.581 + /// The peru.
68.582 + /// </summary>
68.583 + public static readonly OxyColor Peru = OxyColor.FromUInt32(0xFFCD853F);
68.584 +
68.585 + /// <summary>
68.586 + /// The pink.
68.587 + /// </summary>
68.588 + public static readonly OxyColor Pink = OxyColor.FromUInt32(0xFFFFC0CB);
68.589 +
68.590 + /// <summary>
68.591 + /// The plum.
68.592 + /// </summary>
68.593 + public static readonly OxyColor Plum = OxyColor.FromUInt32(0xFFDDA0DD);
68.594 +
68.595 + /// <summary>
68.596 + /// The powder blue.
68.597 + /// </summary>
68.598 + public static readonly OxyColor PowderBlue = OxyColor.FromUInt32(0xFFB0E0E6);
68.599 +
68.600 + /// <summary>
68.601 + /// The purple.
68.602 + /// </summary>
68.603 + public static readonly OxyColor Purple = OxyColor.FromUInt32(0xFF800080);
68.604 +
68.605 + /// <summary>
68.606 + /// The red.
68.607 + /// </summary>
68.608 + public static readonly OxyColor Red = OxyColor.FromUInt32(0xFFFF0000);
68.609 +
68.610 + /// <summary>
68.611 + /// The rosy brown.
68.612 + /// </summary>
68.613 + public static readonly OxyColor RosyBrown = OxyColor.FromUInt32(0xFFBC8F8F);
68.614 +
68.615 + /// <summary>
68.616 + /// The royal blue.
68.617 + /// </summary>
68.618 + public static readonly OxyColor RoyalBlue = OxyColor.FromUInt32(0xFF4169E1);
68.619 +
68.620 + /// <summary>
68.621 + /// The saddle brown.
68.622 + /// </summary>
68.623 + public static readonly OxyColor SaddleBrown = OxyColor.FromUInt32(0xFF8B4513);
68.624 +
68.625 + /// <summary>
68.626 + /// The salmon.
68.627 + /// </summary>
68.628 + public static readonly OxyColor Salmon = OxyColor.FromUInt32(0xFFFA8072);
68.629 +
68.630 + /// <summary>
68.631 + /// The sandy brown.
68.632 + /// </summary>
68.633 + public static readonly OxyColor SandyBrown = OxyColor.FromUInt32(0xFFF4A460);
68.634 +
68.635 + /// <summary>
68.636 + /// The sea green.
68.637 + /// </summary>
68.638 + public static readonly OxyColor SeaGreen = OxyColor.FromUInt32(0xFF2E8B57);
68.639 +
68.640 + /// <summary>
68.641 + /// The sea shell.
68.642 + /// </summary>
68.643 + public static readonly OxyColor SeaShell = OxyColor.FromUInt32(0xFFFFF5EE);
68.644 +
68.645 + /// <summary>
68.646 + /// The sienna.
68.647 + /// </summary>
68.648 + public static readonly OxyColor Sienna = OxyColor.FromUInt32(0xFFA0522D);
68.649 +
68.650 + /// <summary>
68.651 + /// The silver.
68.652 + /// </summary>
68.653 + public static readonly OxyColor Silver = OxyColor.FromUInt32(0xFFC0C0C0);
68.654 +
68.655 + /// <summary>
68.656 + /// The sky blue.
68.657 + /// </summary>
68.658 + public static readonly OxyColor SkyBlue = OxyColor.FromUInt32(0xFF87CEEB);
68.659 +
68.660 + /// <summary>
68.661 + /// The slate blue.
68.662 + /// </summary>
68.663 + public static readonly OxyColor SlateBlue = OxyColor.FromUInt32(0xFF6A5ACD);
68.664 +
68.665 + /// <summary>
68.666 + /// The slate gray.
68.667 + /// </summary>
68.668 + public static readonly OxyColor SlateGray = OxyColor.FromUInt32(0xFF708090);
68.669 +
68.670 + /// <summary>
68.671 + /// The snow.
68.672 + /// </summary>
68.673 + public static readonly OxyColor Snow = OxyColor.FromUInt32(0xFFFFFAFA);
68.674 +
68.675 + /// <summary>
68.676 + /// The spring green.
68.677 + /// </summary>
68.678 + public static readonly OxyColor SpringGreen = OxyColor.FromUInt32(0xFF00FF7F);
68.679 +
68.680 + /// <summary>
68.681 + /// The steel blue.
68.682 + /// </summary>
68.683 + public static readonly OxyColor SteelBlue = OxyColor.FromUInt32(0xFF4682B4);
68.684 +
68.685 + /// <summary>
68.686 + /// The tan.
68.687 + /// </summary>
68.688 + public static readonly OxyColor Tan = OxyColor.FromUInt32(0xFFD2B48C);
68.689 +
68.690 + /// <summary>
68.691 + /// The teal.
68.692 + /// </summary>
68.693 + public static readonly OxyColor Teal = OxyColor.FromUInt32(0xFF008080);
68.694 +
68.695 + /// <summary>
68.696 + /// The thistle.
68.697 + /// </summary>
68.698 + public static readonly OxyColor Thistle = OxyColor.FromUInt32(0xFFD8BFD8);
68.699 +
68.700 + /// <summary>
68.701 + /// The tomato.
68.702 + /// </summary>
68.703 + public static readonly OxyColor Tomato = OxyColor.FromUInt32(0xFFFF6347);
68.704 +
68.705 + /// <summary>
68.706 + /// The transparent.
68.707 + /// </summary>
68.708 + public static readonly OxyColor Transparent = OxyColor.FromUInt32(0x00FFFFFF);
68.709 +
68.710 + /// <summary>
68.711 + /// The turquoise.
68.712 + /// </summary>
68.713 + public static readonly OxyColor Turquoise = OxyColor.FromUInt32(0xFF40E0D0);
68.714 +
68.715 + /// <summary>
68.716 + /// The violet.
68.717 + /// </summary>
68.718 + public static readonly OxyColor Violet = OxyColor.FromUInt32(0xFFEE82EE);
68.719 +
68.720 + /// <summary>
68.721 + /// The wheat.
68.722 + /// </summary>
68.723 + public static readonly OxyColor Wheat = OxyColor.FromUInt32(0xFFF5DEB3);
68.724 +
68.725 + /// <summary>
68.726 + /// The white.
68.727 + /// </summary>
68.728 + public static readonly OxyColor White = OxyColor.FromUInt32(0xFFFFFFFF);
68.729 +
68.730 + /// <summary>
68.731 + /// The white smoke.
68.732 + /// </summary>
68.733 + public static readonly OxyColor WhiteSmoke = OxyColor.FromUInt32(0xFFF5F5F5);
68.734 +
68.735 + /// <summary>
68.736 + /// The yellow.
68.737 + /// </summary>
68.738 + public static readonly OxyColor Yellow = OxyColor.FromUInt32(0xFFFFFF00);
68.739 +
68.740 + /// <summary>
68.741 + /// The yellow green.
68.742 + /// </summary>
68.743 + public static readonly OxyColor YellowGreen = OxyColor.FromUInt32(0xFF9ACD32);
68.744 +
68.745 + }
68.746 +}
68.747 \ No newline at end of file
69.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
69.2 +++ b/External/OxyPlot/OxyPlot/Foundation/OxyImage.cs Sat Jun 08 16:53:22 2013 +0000
69.3 @@ -0,0 +1,444 @@
69.4 +// --------------------------------------------------------------------------------------------------------------------
69.5 +// <copyright file="OxyImage.cs" company="OxyPlot">
69.6 +// The MIT License (MIT)
69.7 +//
69.8 +// Copyright (c) 2012 Oystein Bjorke
69.9 +//
69.10 +// Permission is hereby granted, free of charge, to any person obtaining a
69.11 +// copy of this software and associated documentation files (the
69.12 +// "Software"), to deal in the Software without restriction, including
69.13 +// without limitation the rights to use, copy, modify, merge, publish,
69.14 +// distribute, sublicense, and/or sell copies of the Software, and to
69.15 +// permit persons to whom the Software is furnished to do so, subject to
69.16 +// the following conditions:
69.17 +//
69.18 +// The above copyright notice and this permission notice shall be included
69.19 +// in all copies or substantial portions of the Software.
69.20 +//
69.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
69.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
69.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
69.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
69.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
69.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
69.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
69.28 +// </copyright>
69.29 +// <summary>
69.30 +// Represents an image, encoded as DIB, JPEG or PNG.
69.31 +// </summary>
69.32 +// --------------------------------------------------------------------------------------------------------------------
69.33 +namespace OxyPlot
69.34 +{
69.35 + using System;
69.36 + using System.IO;
69.37 + using System.Linq;
69.38 +
69.39 + /// <summary>
69.40 + /// Represents an image, encoded as DIB, JPEG or PNG.
69.41 + /// </summary>
69.42 + public class OxyImage
69.43 + {
69.44 + /// <summary>
69.45 + /// The image data.
69.46 + /// </summary>
69.47 + private readonly byte[] data;
69.48 +
69.49 + /// <summary>
69.50 + /// Initializes a new instance of the <see cref="OxyImage"/> class from the specified stream.
69.51 + /// </summary>
69.52 + /// <param name="s">
69.53 + /// A stream that provides the image data.
69.54 + /// </param>
69.55 + public OxyImage(Stream s)
69.56 + {
69.57 + using (var ms = new MemoryStream())
69.58 + {
69.59 + s.CopyTo(ms);
69.60 + this.data = ms.ToArray();
69.61 + }
69.62 + }
69.63 +
69.64 + /// <summary>
69.65 + /// Initializes a new instance of the <see cref="OxyImage"/> class from a byte array.
69.66 + /// </summary>
69.67 + /// <param name="bytes">
69.68 + /// The image bytes.
69.69 + /// </param>
69.70 + public OxyImage(byte[] bytes)
69.71 + {
69.72 + this.data = bytes;
69.73 + }
69.74 +
69.75 + /// <summary>
69.76 + /// Creates an <see cref="OxyImage"/> from the specified <see cref="OxyColor"/> array.
69.77 + /// </summary>
69.78 + /// <param name="data">
69.79 + /// The pixel data, indexed as [row,column] (from bottom-left).
69.80 + /// </param>
69.81 + /// <param name="dpi">
69.82 + /// The resolution.
69.83 + /// </param>
69.84 + /// <returns>
69.85 + /// An <see cref="OxyImage"/>.
69.86 + /// </returns>
69.87 + /// <remarks>
69.88 + /// This method is creating a simple BitmapInfoHeader.
69.89 + /// </remarks>
69.90 + public static OxyImage FromArgbX(OxyColor[,] data, int dpi = 96)
69.91 + {
69.92 + int height = data.GetLength(0);
69.93 + int width = data.GetLength(1);
69.94 + var bytes = new byte[width * height * 4];
69.95 + int k = 0;
69.96 + for (int i = 0; i < height; i++)
69.97 + {
69.98 + for (int j = 0; j < width; j++)
69.99 + {
69.100 + bytes[k++] = data[i, j].B;
69.101 + bytes[k++] = data[i, j].G;
69.102 + bytes[k++] = data[i, j].R;
69.103 + bytes[k++] = data[i, j].A;
69.104 + }
69.105 + }
69.106 +
69.107 + return FromArgbX(width, height, bytes, dpi);
69.108 + }
69.109 +
69.110 + /// <summary>
69.111 + /// Creates an <see cref="OxyImage"/> from the specified <see cref="OxyColor"/> array.
69.112 + /// </summary>
69.113 + /// <param name="data">
69.114 + /// The pixel data, indexed as [row,column] (from bottom-left).
69.115 + /// </param>
69.116 + /// <param name="dpi">
69.117 + /// The resolution.
69.118 + /// </param>
69.119 + /// <returns>
69.120 + /// An <see cref="OxyImage"/>.
69.121 + /// </returns>
69.122 + /// <remarks>
69.123 + /// This method is creating a Bitmap V4 info header, including channel bit masks and color space information.
69.124 + /// </remarks>
69.125 + public static OxyImage FromArgb(OxyColor[,] data, int dpi = 96)
69.126 + {
69.127 + int height = data.GetLength(0);
69.128 + int width = data.GetLength(1);
69.129 + var bytes = new byte[width * height * 4];
69.130 + int k = 0;
69.131 + for (int i = 0; i < height; i++)
69.132 + {
69.133 + for (int j = 0; j < width; j++)
69.134 + {
69.135 + bytes[k++] = data[i, j].B;
69.136 + bytes[k++] = data[i, j].G;
69.137 + bytes[k++] = data[i, j].R;
69.138 + bytes[k++] = data[i, j].A;
69.139 + }
69.140 + }
69.141 +
69.142 + return FromArgb(width, height, bytes, dpi);
69.143 + }
69.144 +
69.145 + /// <summary>
69.146 + /// Creates an <see cref="OxyImage"/> from the specified pixel data.
69.147 + /// </summary>
69.148 + /// <param name="width">
69.149 + /// The width.
69.150 + /// </param>
69.151 + /// <param name="height">
69.152 + /// The height.
69.153 + /// </param>
69.154 + /// <param name="pixelData">
69.155 + /// The pixel data (BGRA from bottom-left).
69.156 + /// </param>
69.157 + /// <param name="dpi">
69.158 + /// The resolution.
69.159 + /// </param>
69.160 + /// <returns>
69.161 + /// An <see cref="OxyImage"/>.
69.162 + /// </returns>
69.163 + /// <remarks>
69.164 + /// This method is creating a Bitmap V4 info header, including channel bit masks and color space information.
69.165 + /// </remarks>
69.166 + public static OxyImage FromArgb(int width, int height, byte[] pixelData, int dpi = 96)
69.167 + {
69.168 + var ms = new MemoryStream();
69.169 + var w = new BinaryWriter(ms);
69.170 +
69.171 + const int OffBits = 14 + 108;
69.172 + var size = OffBits + pixelData.Length;
69.173 +
69.174 + // Bitmap file header (14 bytes)
69.175 + w.Write((byte)'B');
69.176 + w.Write((byte)'M');
69.177 + w.Write((uint)size);
69.178 + w.Write((ushort)0);
69.179 + w.Write((ushort)0);
69.180 + w.Write((uint)OffBits);
69.181 +
69.182 + // Bitmap V4 info header (108 bytes)
69.183 + WriteBitmapV4Header(w, width, height, 32, pixelData.Length, dpi);
69.184 +
69.185 + // Pixel array (from bottom-left corner)
69.186 + w.Write(pixelData);
69.187 +
69.188 + return new OxyImage(ms.ToArray());
69.189 + }
69.190 +
69.191 + /// <summary>
69.192 + /// Creates an <see cref="OxyImage"/> from the specified 8-bit indexed pixel data.
69.193 + /// </summary>
69.194 + /// <param name="indexedData">
69.195 + /// The indexed pixel data (from bottom-left).
69.196 + /// </param>
69.197 + /// <param name="palette">
69.198 + /// The palette.
69.199 + /// </param>
69.200 + /// <param name="dpi">
69.201 + /// The resolution.
69.202 + /// </param>
69.203 + /// <returns>
69.204 + /// An <see cref="OxyImage"/>.
69.205 + /// </returns>
69.206 + public static OxyImage FromIndexed8(byte[,] indexedData, OxyColor[] palette, int dpi = 96)
69.207 + {
69.208 + int height = indexedData.GetLength(0);
69.209 + int width = indexedData.GetLength(1);
69.210 + return FromIndexed8(width, height, indexedData.Cast<byte>().ToArray(), palette, dpi);
69.211 + }
69.212 +
69.213 + /// <summary>
69.214 + /// Creates an <see cref="OxyImage"/> from the specified 8-bit indexed pixel data.
69.215 + /// </summary>
69.216 + /// <param name="width">
69.217 + /// The width.
69.218 + /// </param>
69.219 + /// <param name="height">
69.220 + /// The height.
69.221 + /// </param>
69.222 + /// <param name="indexedPixelData">
69.223 + /// The indexed pixel data (from bottom-left).
69.224 + /// </param>
69.225 + /// <param name="palette">
69.226 + /// The palette.
69.227 + /// </param>
69.228 + /// <param name="dpi">
69.229 + /// The resolution.
69.230 + /// </param>
69.231 + /// <returns>
69.232 + /// An <see cref="OxyImage"/>.
69.233 + /// </returns>
69.234 + public static OxyImage FromIndexed8(
69.235 + int width, int height, byte[] indexedPixelData, OxyColor[] palette, int dpi = 96)
69.236 + {
69.237 + if (indexedPixelData.Length != width * height)
69.238 + {
69.239 + throw new ArgumentException("Length of data is not correct.", "indexedPixelData");
69.240 + }
69.241 +
69.242 + if (palette.Length == 0)
69.243 + {
69.244 + throw new ArgumentException("Palette not defined.", "palette");
69.245 + }
69.246 +
69.247 + var ms = new MemoryStream();
69.248 + var w = new BinaryWriter(ms);
69.249 +
69.250 + var offBits = 14 + 40 + (4 * palette.Length);
69.251 + var size = offBits + indexedPixelData.Length;
69.252 +
69.253 + // Bitmap file header (14 bytes)
69.254 + w.Write((byte)'B');
69.255 + w.Write((byte)'M');
69.256 + w.Write((uint)size);
69.257 + w.Write((ushort)0);
69.258 + w.Write((ushort)0);
69.259 + w.Write((uint)offBits);
69.260 +
69.261 + // Bitmap info header
69.262 + WriteBitmapInfoHeader(w, width, height, 8, indexedPixelData.Length, dpi, palette.Length);
69.263 +
69.264 + // Color table
69.265 + foreach (var color in palette)
69.266 + {
69.267 + w.Write(color.B);
69.268 + w.Write(color.G);
69.269 + w.Write(color.R);
69.270 + w.Write(color.A);
69.271 + }
69.272 +
69.273 + // Pixel array (from bottom-left corner)
69.274 + w.Write(indexedPixelData);
69.275 +
69.276 + return new OxyImage(ms.ToArray());
69.277 + }
69.278 +
69.279 + /// <summary>
69.280 + /// Creates an <see cref="OxyImage"/> from the specified pixel data.
69.281 + /// </summary>
69.282 + /// <param name="width">
69.283 + /// The width.
69.284 + /// </param>
69.285 + /// <param name="height">
69.286 + /// The height.
69.287 + /// </param>
69.288 + /// <param name="pixelData">
69.289 + /// The pixel data (BGRA from bottom-left).
69.290 + /// </param>
69.291 + /// <param name="dpi">
69.292 + /// The resolution.
69.293 + /// </param>
69.294 + /// <returns>
69.295 + /// An <see cref="OxyImage"/>.
69.296 + /// </returns>
69.297 + /// <remarks>
69.298 + /// This method is creating a simple BitmapInfoHeader.
69.299 + /// </remarks>
69.300 + public static OxyImage FromArgbX(int width, int height, byte[] pixelData, int dpi = 96)
69.301 + {
69.302 + var ms = new MemoryStream();
69.303 + var w = new BinaryWriter(ms);
69.304 +
69.305 + const int OffBits = 14 + 40;
69.306 + var size = OffBits + pixelData.Length;
69.307 +
69.308 + // Bitmap file header (14 bytes)
69.309 + w.Write((byte)'B');
69.310 + w.Write((byte)'M');
69.311 + w.Write((uint)size);
69.312 + w.Write((ushort)0);
69.313 + w.Write((ushort)0);
69.314 + w.Write((uint)OffBits);
69.315 +
69.316 + // Bitmap info header
69.317 + WriteBitmapInfoHeader(w, width, height, 32, pixelData.Length, dpi);
69.318 +
69.319 + // Pixel array (from bottom-left corner)
69.320 + w.Write(pixelData);
69.321 +
69.322 + return new OxyImage(ms.ToArray());
69.323 + }
69.324 +
69.325 + /// <summary>
69.326 + /// Gets the image data.
69.327 + /// </summary>
69.328 + /// <returns>
69.329 + /// The image data as a byte array.
69.330 + /// </returns>
69.331 + public byte[] GetData()
69.332 + {
69.333 + return this.data;
69.334 + }
69.335 +
69.336 + /// <summary>
69.337 + /// Writes the bitmap info header.
69.338 + /// </summary>
69.339 + /// <param name="w">
69.340 + /// The writer.
69.341 + /// </param>
69.342 + /// <param name="width">
69.343 + /// The width.
69.344 + /// </param>
69.345 + /// <param name="height">
69.346 + /// The height.
69.347 + /// </param>
69.348 + /// <param name="bitsPerPixel">
69.349 + /// The number of bits per pixel.
69.350 + /// </param>
69.351 + /// <param name="length">
69.352 + /// The length of the pixel data.
69.353 + /// </param>
69.354 + /// <param name="dpi">
69.355 + /// The dpi.
69.356 + /// </param>
69.357 + /// <param name="colors">
69.358 + /// The number of colors.
69.359 + /// </param>
69.360 + private static void WriteBitmapInfoHeader(
69.361 + BinaryWriter w, int width, int height, int bitsPerPixel, int length, int dpi, int colors = 0)
69.362 + {
69.363 + // Convert resolution to pixels per meter
69.364 + var ppm = (uint)(dpi / 0.0254);
69.365 +
69.366 + w.Write((uint)40);
69.367 + w.Write((uint)width);
69.368 + w.Write((uint)height);
69.369 + w.Write((ushort)1);
69.370 + w.Write((ushort)bitsPerPixel);
69.371 + w.Write((uint)0);
69.372 + w.Write((uint)length);
69.373 + w.Write(ppm);
69.374 + w.Write(ppm);
69.375 + w.Write((uint)colors);
69.376 + w.Write((uint)colors);
69.377 + }
69.378 +
69.379 + /// <summary>
69.380 + /// Writes the bitmap V4 header.
69.381 + /// </summary>
69.382 + /// <param name="w">
69.383 + /// The writer.
69.384 + /// </param>
69.385 + /// <param name="width">
69.386 + /// The width.
69.387 + /// </param>
69.388 + /// <param name="height">
69.389 + /// The height.
69.390 + /// </param>
69.391 + /// <param name="bitsPerPixel">
69.392 + /// The number of bits per pixel.
69.393 + /// </param>
69.394 + /// <param name="length">
69.395 + /// The length.
69.396 + /// </param>
69.397 + /// <param name="dpi">
69.398 + /// The resolution.
69.399 + /// </param>
69.400 + /// <param name="colors">
69.401 + /// The number of colors.
69.402 + /// </param>
69.403 + private static void WriteBitmapV4Header(
69.404 + BinaryWriter w, int width, int height, int bitsPerPixel, int length, int dpi, int colors = 0)
69.405 + {
69.406 + // Convert resolution to pixels per meter
69.407 + var ppm = (uint)(dpi / 0.0254);
69.408 +
69.409 + w.Write((uint)108);
69.410 + w.Write((uint)width);
69.411 + w.Write((uint)height);
69.412 + w.Write((ushort)1);
69.413 + w.Write((ushort)bitsPerPixel);
69.414 + w.Write((uint)3);
69.415 + w.Write((uint)length);
69.416 + w.Write(ppm);
69.417 + w.Write(ppm);
69.418 + w.Write((uint)colors);
69.419 + w.Write((uint)colors);
69.420 +
69.421 + // Write the channel bit masks
69.422 + w.Write(0x00FF0000);
69.423 + w.Write(0x0000FF00);
69.424 + w.Write(0x000000FF);
69.425 + w.Write(0xFF000000);
69.426 +
69.427 + // Write the color space
69.428 + w.Write((uint)0x206E6957);
69.429 + w.Write(new byte[3 * 3 * 4]);
69.430 +
69.431 + // Write the gamma RGB
69.432 + w.Write((uint)0);
69.433 + w.Write((uint)0);
69.434 + w.Write((uint)0);
69.435 + }
69.436 +
69.437 + /// <summary>
69.438 + /// Creates a PNG image from the specified pixels.
69.439 + /// </summary>
69.440 + /// <param name="pixels">The pixels (bottom line first).</param>
69.441 + /// <returns>An OxyImage.</returns>
69.442 + public static OxyImage PngFromArgb(OxyColor[,] pixels)
69.443 + {
69.444 + return new OxyImage(PngEncoder.Encode(pixels));
69.445 + }
69.446 + }
69.447 +}
69.448 \ No newline at end of file
70.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
70.2 +++ b/External/OxyPlot/OxyPlot/Foundation/OxyPalette.cs Sat Jun 08 16:53:22 2013 +0000
70.3 @@ -0,0 +1,102 @@
70.4 +// --------------------------------------------------------------------------------------------------------------------
70.5 +// <copyright file="OxyPalette.cs" company="OxyPlot">
70.6 +// The MIT License (MIT)
70.7 +//
70.8 +// Copyright (c) 2012 Oystein Bjorke
70.9 +//
70.10 +// Permission is hereby granted, free of charge, to any person obtaining a
70.11 +// copy of this software and associated documentation files (the
70.12 +// "Software"), to deal in the Software without restriction, including
70.13 +// without limitation the rights to use, copy, modify, merge, publish,
70.14 +// distribute, sublicense, and/or sell copies of the Software, and to
70.15 +// permit persons to whom the Software is furnished to do so, subject to
70.16 +// the following conditions:
70.17 +//
70.18 +// The above copyright notice and this permission notice shall be included
70.19 +// in all copies or substantial portions of the Software.
70.20 +//
70.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
70.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
70.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
70.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
70.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
70.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
70.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
70.28 +// </copyright>
70.29 +// <summary>
70.30 +// Represents a palette of colors.
70.31 +// </summary>
70.32 +// --------------------------------------------------------------------------------------------------------------------
70.33 +namespace OxyPlot
70.34 +{
70.35 + using System.Collections.Generic;
70.36 +
70.37 + /// <summary>
70.38 + /// Represents a palette of colors.
70.39 + /// </summary>
70.40 + public class OxyPalette
70.41 + {
70.42 + /// <summary>
70.43 + /// Initializes a new instance of the <see cref="OxyPalette"/> class.
70.44 + /// </summary>
70.45 + public OxyPalette()
70.46 + {
70.47 + this.Colors = new List<OxyColor>();
70.48 + }
70.49 +
70.50 + /// <summary>
70.51 + /// Initializes a new instance of the <see cref="OxyPalette"/> class.
70.52 + /// </summary>
70.53 + /// <param name="colors">
70.54 + /// The colors.
70.55 + /// </param>
70.56 + public OxyPalette(params OxyColor[] colors)
70.57 + {
70.58 + this.Colors = new List<OxyColor>(colors);
70.59 + }
70.60 +
70.61 + /// <summary>
70.62 + /// Initializes a new instance of the <see cref="OxyPalette"/> class.
70.63 + /// </summary>
70.64 + /// <param name="colors">
70.65 + /// The colors.
70.66 + /// </param>
70.67 + public OxyPalette(IEnumerable<OxyColor> colors)
70.68 + {
70.69 + this.Colors = new List<OxyColor>(colors);
70.70 + }
70.71 +
70.72 + /// <summary>
70.73 + /// Gets or sets the colors.
70.74 + /// </summary>
70.75 + /// <value> The colors. </value>
70.76 + public IList<OxyColor> Colors { get; set; }
70.77 +
70.78 + /// <summary>
70.79 + /// Interpolates the specified colors to a palette of the specified size.
70.80 + /// </summary>
70.81 + /// <param name="paletteSize">
70.82 + /// The size of the palette.
70.83 + /// </param>
70.84 + /// <param name="colors">
70.85 + /// The colors.
70.86 + /// </param>
70.87 + /// <returns>
70.88 + /// A palette.
70.89 + /// </returns>
70.90 + public static OxyPalette Interpolate(int paletteSize, params OxyColor[] colors)
70.91 + {
70.92 + var palette = new OxyColor[paletteSize];
70.93 + for (int i = 0; i < paletteSize; i++)
70.94 + {
70.95 + double y = (double)i / (paletteSize - 1);
70.96 + double x = y * (colors.Length - 1);
70.97 + int i0 = (int)x;
70.98 + int i1 = i0 + 1 < colors.Length ? i0 + 1 : i0;
70.99 + palette[i] = OxyColor.Interpolate(colors[i0], colors[i1], x - i0);
70.100 + }
70.101 +
70.102 + return new OxyPalette(palette);
70.103 + }
70.104 + }
70.105 +}
70.106 \ No newline at end of file
71.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
71.2 +++ b/External/OxyPlot/OxyPlot/Foundation/OxyPalettes.cs Sat Jun 08 16:53:22 2013 +0000
71.3 @@ -0,0 +1,208 @@
71.4 +// --------------------------------------------------------------------------------------------------------------------
71.5 +// <copyright file="OxyPalettes.cs" company="OxyPlot">
71.6 +// The MIT License (MIT)
71.7 +//
71.8 +// Copyright (c) 2012 Oystein Bjorke
71.9 +//
71.10 +// Permission is hereby granted, free of charge, to any person obtaining a
71.11 +// copy of this software and associated documentation files (the
71.12 +// "Software"), to deal in the Software without restriction, including
71.13 +// without limitation the rights to use, copy, modify, merge, publish,
71.14 +// distribute, sublicense, and/or sell copies of the Software, and to
71.15 +// permit persons to whom the Software is furnished to do so, subject to
71.16 +// the following conditions:
71.17 +//
71.18 +// The above copyright notice and this permission notice shall be included
71.19 +// in all copies or substantial portions of the Software.
71.20 +//
71.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
71.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
71.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
71.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
71.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
71.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
71.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
71.28 +// </copyright>
71.29 +// <summary>
71.30 +// Provides predefined palettes.
71.31 +// </summary>
71.32 +// --------------------------------------------------------------------------------------------------------------------
71.33 +namespace OxyPlot
71.34 +{
71.35 + /// <summary>
71.36 + /// Provides predefined palettes.
71.37 + /// </summary>
71.38 + public static class OxyPalettes
71.39 + {
71.40 + /// <summary>
71.41 + /// Initializes static members of the <see cref="OxyPalettes"/> class.
71.42 + /// </summary>
71.43 + static OxyPalettes()
71.44 + {
71.45 + BlueWhiteRed31 = BlueWhiteRed(31);
71.46 + Hot64 = Hot(64);
71.47 + Hue64 = Hue(64);
71.48 + }
71.49 +
71.50 + /// <summary>
71.51 + /// Gets the blue white red (31) palette.
71.52 + /// </summary>
71.53 + public static OxyPalette BlueWhiteRed31 { get; private set; }
71.54 +
71.55 + /// <summary>
71.56 + /// Gets the hot (64) palette.
71.57 + /// </summary>
71.58 + public static OxyPalette Hot64 { get; private set; }
71.59 +
71.60 + /// <summary>
71.61 + /// Gets the hue64 palette.
71.62 + /// </summary>
71.63 + public static OxyPalette Hue64 { get; private set; }
71.64 +
71.65 + /// <summary>
71.66 + /// Creates a black/white/red palette with the specified number of colors.
71.67 + /// </summary>
71.68 + /// <param name="numberOfColors">
71.69 + /// The number of colors to create for the palette.
71.70 + /// </param>
71.71 + /// <returns>
71.72 + /// A palette.
71.73 + /// </returns>
71.74 + public static OxyPalette BlackWhiteRed(int numberOfColors)
71.75 + {
71.76 + return OxyPalette.Interpolate(numberOfColors, OxyColors.Black, OxyColors.White, OxyColors.Red);
71.77 + }
71.78 +
71.79 + /// <summary>
71.80 + /// Creates a blue/white/red palette with the specified number of colors.
71.81 + /// </summary>
71.82 + /// <param name="numberOfColors">
71.83 + /// The number of colors to create for the palette.
71.84 + /// </param>
71.85 + /// <returns>
71.86 + /// A palette.
71.87 + /// </returns>
71.88 + public static OxyPalette BlueWhiteRed(int numberOfColors)
71.89 + {
71.90 + return OxyPalette.Interpolate(numberOfColors, OxyColors.Blue, OxyColors.White, OxyColors.Red);
71.91 + }
71.92 +
71.93 + /// <summary>
71.94 + /// Creates a 'cool' palette with the specified number of colors.
71.95 + /// </summary>
71.96 + /// <param name="numberOfColors">
71.97 + /// The number of colors to create for the palette.
71.98 + /// </param>
71.99 + /// <returns>
71.100 + /// A palette.
71.101 + /// </returns>
71.102 + public static OxyPalette Cool(int numberOfColors)
71.103 + {
71.104 + return OxyPalette.Interpolate(numberOfColors, OxyColors.Cyan, OxyColors.Magenta);
71.105 + }
71.106 +
71.107 + /// <summary>
71.108 + /// Creates a gray-scale palette with the specified number of colors.
71.109 + /// </summary>
71.110 + /// <param name="numberOfColors">
71.111 + /// The number of colors to create for the palette.
71.112 + /// </param>
71.113 + /// <returns>
71.114 + /// A palette.
71.115 + /// </returns>
71.116 + public static OxyPalette Gray(int numberOfColors)
71.117 + {
71.118 + return OxyPalette.Interpolate(numberOfColors, OxyColors.Black, OxyColors.White);
71.119 + }
71.120 +
71.121 + /// <summary>
71.122 + /// Creates a 'hot' palette with the specified number of colors.
71.123 + /// </summary>
71.124 + /// <param name="numberOfColors">
71.125 + /// The number of colors to create for the palette.
71.126 + /// </param>
71.127 + /// <returns>
71.128 + /// A palette.
71.129 + /// </returns>
71.130 + public static OxyPalette Hot(int numberOfColors)
71.131 + {
71.132 + return OxyPalette.Interpolate(
71.133 + numberOfColors,
71.134 + OxyColors.Black,
71.135 + OxyColor.FromRgb(127, 0, 0),
71.136 + OxyColor.FromRgb(255, 127, 0),
71.137 + OxyColor.FromRgb(255, 255, 127),
71.138 + OxyColors.White);
71.139 + }
71.140 +
71.141 + /// <summary>
71.142 + /// Creates a palette from the hue component of the HSV color model.
71.143 + /// </summary>
71.144 + /// <param name="numberOfColors">
71.145 + /// The number of colors.
71.146 + /// </param>
71.147 + /// <returns>
71.148 + /// The palette.
71.149 + /// </returns>
71.150 + /// <remarks>
71.151 + /// This palette is particularly appropriate for displaying periodic functions.
71.152 + /// </remarks>
71.153 + public static OxyPalette Hue(int numberOfColors)
71.154 + {
71.155 + return OxyPalette.Interpolate(
71.156 + numberOfColors,
71.157 + OxyColors.Red,
71.158 + OxyColors.Yellow,
71.159 + OxyColors.Green,
71.160 + OxyColors.Cyan,
71.161 + OxyColors.Blue,
71.162 + OxyColors.Magenta,
71.163 + OxyColors.Red);
71.164 + }
71.165 +
71.166 + /// <summary>
71.167 + /// Creates a 'jet' palette with the specified number of colors.
71.168 + /// </summary>
71.169 + /// <param name="numberOfColors">
71.170 + /// The number of colors to create for the palette.
71.171 + /// </param>
71.172 + /// <returns>
71.173 + /// A palette.
71.174 + /// </returns>
71.175 + /// <remarks>
71.176 + /// See http://www.mathworks.se/help/techdoc/ref/colormap.html.
71.177 + /// </remarks>
71.178 + public static OxyPalette Jet(int numberOfColors)
71.179 + {
71.180 + return OxyPalette.Interpolate(
71.181 + numberOfColors,
71.182 + OxyColors.DarkBlue,
71.183 + OxyColors.Cyan,
71.184 + OxyColors.Yellow,
71.185 + OxyColors.Orange,
71.186 + OxyColors.DarkRed);
71.187 + }
71.188 +
71.189 + /// <summary>
71.190 + /// Creates a rainbow palette with the specified number of colors.
71.191 + /// </summary>
71.192 + /// <param name="numberOfColors">
71.193 + /// The number of colors to create for the palette.
71.194 + /// </param>
71.195 + /// <returns>
71.196 + /// A palette.
71.197 + /// </returns>
71.198 + public static OxyPalette Rainbow(int numberOfColors)
71.199 + {
71.200 + return OxyPalette.Interpolate(
71.201 + numberOfColors,
71.202 + OxyColors.Violet,
71.203 + OxyColors.Indigo,
71.204 + OxyColors.Blue,
71.205 + OxyColors.Green,
71.206 + OxyColors.Yellow,
71.207 + OxyColors.Orange,
71.208 + OxyColors.Red);
71.209 + }
71.210 + }
71.211 +}
71.212 \ No newline at end of file
72.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
72.2 +++ b/External/OxyPlot/OxyPlot/Foundation/OxyPen.cs Sat Jun 08 16:53:22 2013 +0000
72.3 @@ -0,0 +1,138 @@
72.4 +// --------------------------------------------------------------------------------------------------------------------
72.5 +// <copyright file="OxyPen.cs" company="OxyPlot">
72.6 +// The MIT License (MIT)
72.7 +//
72.8 +// Copyright (c) 2012 Oystein Bjorke
72.9 +//
72.10 +// Permission is hereby granted, free of charge, to any person obtaining a
72.11 +// copy of this software and associated documentation files (the
72.12 +// "Software"), to deal in the Software without restriction, including
72.13 +// without limitation the rights to use, copy, modify, merge, publish,
72.14 +// distribute, sublicense, and/or sell copies of the Software, and to
72.15 +// permit persons to whom the Software is furnished to do so, subject to
72.16 +// the following conditions:
72.17 +//
72.18 +// The above copyright notice and this permission notice shall be included
72.19 +// in all copies or substantial portions of the Software.
72.20 +//
72.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
72.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
72.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
72.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
72.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
72.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
72.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
72.28 +// </copyright>
72.29 +// <summary>
72.30 +// Describes a pen in terms of color, thickness, line style and line join type.
72.31 +// </summary>
72.32 +// --------------------------------------------------------------------------------------------------------------------
72.33 +namespace OxyPlot
72.34 +{
72.35 + using System;
72.36 +
72.37 + /// <summary>
72.38 + /// Describes a pen in terms of color, thickness, line style and line join type.
72.39 + /// </summary>
72.40 + public class OxyPen
72.41 + {
72.42 + /// <summary>
72.43 + /// Initializes a new instance of the <see cref="OxyPen"/> class.
72.44 + /// </summary>
72.45 + /// <param name="color">
72.46 + /// The color.
72.47 + /// </param>
72.48 + /// <param name="thickness">
72.49 + /// The thickness.
72.50 + /// </param>
72.51 + /// <param name="lineStyle">
72.52 + /// The line style.
72.53 + /// </param>
72.54 + /// <param name="lineJoin">
72.55 + /// The line join.
72.56 + /// </param>
72.57 + public OxyPen(
72.58 + OxyColor color,
72.59 + double thickness = 1.0,
72.60 + LineStyle lineStyle = LineStyle.Solid,
72.61 + OxyPenLineJoin lineJoin = OxyPenLineJoin.Miter)
72.62 + {
72.63 + this.Color = color;
72.64 + this.Thickness = thickness;
72.65 + this.DashArray = LineStyleHelper.GetDashArray(lineStyle);
72.66 + this.LineStyle = lineStyle;
72.67 + this.LineJoin = lineJoin;
72.68 + }
72.69 +
72.70 + /// <summary>
72.71 + /// Gets or sets the color.
72.72 + /// </summary>
72.73 + /// <value>The color.</value>
72.74 + public OxyColor Color { get; set; }
72.75 +
72.76 + /// <summary>
72.77 + /// Gets or sets the dash array.
72.78 + /// </summary>
72.79 + /// <value>The dash array.</value>
72.80 + public double[] DashArray { get; set; }
72.81 +
72.82 + /// <summary>
72.83 + /// Gets or sets the line join.
72.84 + /// </summary>
72.85 + /// <value>The line join.</value>
72.86 + public OxyPenLineJoin LineJoin { get; set; }
72.87 +
72.88 + /// <summary>
72.89 + /// Gets or sets the line style.
72.90 + /// </summary>
72.91 + /// <value>The line style.</value>
72.92 + public LineStyle LineStyle { get; set; }
72.93 +
72.94 + /// <summary>
72.95 + /// Gets or sets the thickness.
72.96 + /// </summary>
72.97 + /// <value>The thickness.</value>
72.98 + public double Thickness { get; set; }
72.99 +
72.100 + /// <summary>
72.101 + /// Creates the specified pen.
72.102 + /// </summary>
72.103 + /// <param name="color">The color.</param>
72.104 + /// <param name="thickness">The thickness.</param>
72.105 + /// <param name="lineStyle">The line style.</param>
72.106 + /// <param name="lineJoin">The line join.</param>
72.107 + /// <returns>A pen.</returns>
72.108 + public static OxyPen Create(
72.109 + OxyColor color,
72.110 + double thickness,
72.111 + LineStyle lineStyle = LineStyle.Solid,
72.112 + OxyPenLineJoin lineJoin = OxyPenLineJoin.Miter)
72.113 + {
72.114 + if (color == null || lineStyle == LineStyle.None || Math.Abs(thickness) < double.Epsilon)
72.115 + {
72.116 + return null;
72.117 + }
72.118 +
72.119 + return new OxyPen(color, thickness, lineStyle, lineJoin);
72.120 + }
72.121 +
72.122 + /// <summary>
72.123 + /// Returns a hash code for this instance.
72.124 + /// </summary>
72.125 + /// <returns>
72.126 + /// A hash code for this instance, suitable for use in hashing algorithms and data structures like a hash table.
72.127 + /// </returns>
72.128 + public override int GetHashCode()
72.129 + {
72.130 + unchecked
72.131 + {
72.132 + int result = this.Color.GetHashCode();
72.133 + result = (result * 397) ^ this.Thickness.GetHashCode();
72.134 + result = (result * 397) ^ this.LineStyle.GetHashCode();
72.135 + result = (result * 397) ^ this.LineJoin.GetHashCode();
72.136 + return result;
72.137 + }
72.138 + }
72.139 +
72.140 + }
72.141 +}
72.142 \ No newline at end of file
73.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
73.2 +++ b/External/OxyPlot/OxyPlot/Foundation/OxyPenLineJoin.cs Sat Jun 08 16:53:22 2013 +0000
73.3 @@ -0,0 +1,52 @@
73.4 +// --------------------------------------------------------------------------------------------------------------------
73.5 +// <copyright file="OxyPenLineJoin.cs" company="OxyPlot">
73.6 +// The MIT License (MIT)
73.7 +//
73.8 +// Copyright (c) 2012 Oystein Bjorke
73.9 +//
73.10 +// Permission is hereby granted, free of charge, to any person obtaining a
73.11 +// copy of this software and associated documentation files (the
73.12 +// "Software"), to deal in the Software without restriction, including
73.13 +// without limitation the rights to use, copy, modify, merge, publish,
73.14 +// distribute, sublicense, and/or sell copies of the Software, and to
73.15 +// permit persons to whom the Software is furnished to do so, subject to
73.16 +// the following conditions:
73.17 +//
73.18 +// The above copyright notice and this permission notice shall be included
73.19 +// in all copies or substantial portions of the Software.
73.20 +//
73.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
73.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
73.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
73.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
73.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
73.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
73.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
73.28 +// </copyright>
73.29 +// <summary>
73.30 +// Pen line join.
73.31 +// </summary>
73.32 +// --------------------------------------------------------------------------------------------------------------------
73.33 +namespace OxyPlot
73.34 +{
73.35 + /// <summary>
73.36 + /// Specifies how to join line segments.
73.37 + /// </summary>
73.38 + public enum OxyPenLineJoin
73.39 + {
73.40 + /// <summary>
73.41 + /// Line joins use regular angular vertices.
73.42 + /// </summary>
73.43 + Miter,
73.44 +
73.45 + /// <summary>
73.46 + /// Line joins use rounded vertices.
73.47 + /// </summary>
73.48 + Round,
73.49 +
73.50 + /// <summary>
73.51 + /// Line joins use beveled vertices.
73.52 + /// </summary>
73.53 + Bevel
73.54 + }
73.55 +}
73.56 \ No newline at end of file
74.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
74.2 +++ b/External/OxyPlot/OxyPlot/Foundation/OxyRect.cs Sat Jun 08 16:53:22 2013 +0000
74.3 @@ -0,0 +1,287 @@
74.4 +// --------------------------------------------------------------------------------------------------------------------
74.5 +// <copyright file="OxyRect.cs" company="OxyPlot">
74.6 +// The MIT License (MIT)
74.7 +//
74.8 +// Copyright (c) 2012 Oystein Bjorke
74.9 +//
74.10 +// Permission is hereby granted, free of charge, to any person obtaining a
74.11 +// copy of this software and associated documentation files (the
74.12 +// "Software"), to deal in the Software without restriction, including
74.13 +// without limitation the rights to use, copy, modify, merge, publish,
74.14 +// distribute, sublicense, and/or sell copies of the Software, and to
74.15 +// permit persons to whom the Software is furnished to do so, subject to
74.16 +// the following conditions:
74.17 +//
74.18 +// The above copyright notice and this permission notice shall be included
74.19 +// in all copies or substantial portions of the Software.
74.20 +//
74.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
74.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
74.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
74.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
74.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
74.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
74.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
74.28 +// </copyright>
74.29 +// <summary>
74.30 +// Describes the width, height, and point origin of a rectangle.
74.31 +// </summary>
74.32 +// --------------------------------------------------------------------------------------------------------------------
74.33 +namespace OxyPlot
74.34 +{
74.35 + using System;
74.36 + using System.Diagnostics;
74.37 + using System.Globalization;
74.38 +
74.39 + /// <summary>
74.40 + /// Describes the width, height, and point origin of a rectangle.
74.41 + /// </summary>
74.42 + public struct OxyRect
74.43 + {
74.44 + /// <summary>
74.45 + /// The height of the rectangle.
74.46 + /// </summary>
74.47 + private double height;
74.48 +
74.49 + /// <summary>
74.50 + /// The x-coordinate location of the left side of the rectangle.
74.51 + /// </summary>
74.52 + private double left;
74.53 +
74.54 + /// <summary>
74.55 + /// The y-coordinate location of the top side of the rectangle.
74.56 + /// </summary>
74.57 + private double top;
74.58 +
74.59 + /// <summary>
74.60 + /// The width of the rectangle.
74.61 + /// </summary>
74.62 + private double width;
74.63 +
74.64 + /// <summary>
74.65 + /// Initializes a new instance of the <see cref="OxyRect"/> structure that has the specified x-coordinate, y-coordinate, width, and height.
74.66 + /// </summary>
74.67 + /// <param name="left">
74.68 + /// The x-coordinate location of the left side of the rectangle.
74.69 + /// </param>
74.70 + /// <param name="top">
74.71 + /// The y-coordinate location of the top side of the rectangle.
74.72 + /// </param>
74.73 + /// <param name="width">
74.74 + /// The width of the rectangle.
74.75 + /// </param>
74.76 + /// <param name="height">
74.77 + /// The height of the rectangle.
74.78 + /// </param>
74.79 + public OxyRect(double left, double top, double width, double height)
74.80 + {
74.81 + this.left = left;
74.82 + this.top = top;
74.83 + this.width = width;
74.84 + this.height = height;
74.85 + Debug.Assert(width >= 0, "Width should be larger than 0.");
74.86 + Debug.Assert(height >= 0, "Height should be larger than 0.");
74.87 + }
74.88 +
74.89 + /// <summary>
74.90 + /// Gets or sets the y-axis value of the bottom of the rectangle.
74.91 + /// </summary>
74.92 + /// <value>
74.93 + /// The bottom.
74.94 + /// </value>
74.95 + public double Bottom
74.96 + {
74.97 + get
74.98 + {
74.99 + return this.top + this.height;
74.100 + }
74.101 +
74.102 + set
74.103 + {
74.104 + this.height = value - this.top;
74.105 + }
74.106 + }
74.107 +
74.108 + /// <summary>
74.109 + /// Gets or sets the height of the rectangle.
74.110 + /// </summary>
74.111 + /// <value>
74.112 + /// The height.
74.113 + /// </value>
74.114 + public double Height
74.115 + {
74.116 + get
74.117 + {
74.118 + return this.height;
74.119 + }
74.120 +
74.121 + set
74.122 + {
74.123 + this.height = value;
74.124 + }
74.125 + }
74.126 +
74.127 + /// <summary>
74.128 + /// Gets or sets the x-axis value of the left side of the rectangle.
74.129 + /// </summary>
74.130 + /// <value>
74.131 + /// The left.
74.132 + /// </value>
74.133 + public double Left
74.134 + {
74.135 + get
74.136 + {
74.137 + return this.left;
74.138 + }
74.139 +
74.140 + set
74.141 + {
74.142 + this.left = value;
74.143 + }
74.144 + }
74.145 +
74.146 + /// <summary>
74.147 + /// Gets or sets the x-axis value of the right side of the rectangle.
74.148 + /// </summary>
74.149 + /// <value>
74.150 + /// The right.
74.151 + /// </value>
74.152 + public double Right
74.153 + {
74.154 + get
74.155 + {
74.156 + return this.left + this.width;
74.157 + }
74.158 +
74.159 + set
74.160 + {
74.161 + this.width = value - this.left;
74.162 + }
74.163 + }
74.164 +
74.165 + /// <summary>
74.166 + /// Gets or sets the y-axis position of the top of the rectangle.
74.167 + /// </summary>
74.168 + /// <value>
74.169 + /// The top.
74.170 + /// </value>
74.171 + public double Top
74.172 + {
74.173 + get
74.174 + {
74.175 + return this.top;
74.176 + }
74.177 +
74.178 + set
74.179 + {
74.180 + this.top = value;
74.181 + }
74.182 + }
74.183 +
74.184 + /// <summary>
74.185 + /// Gets or sets the width of the rectangle.
74.186 + /// </summary>
74.187 + /// <value>
74.188 + /// The width.
74.189 + /// </value>
74.190 + public double Width
74.191 + {
74.192 + get
74.193 + {
74.194 + return this.width;
74.195 + }
74.196 +
74.197 + set
74.198 + {
74.199 + this.width = value;
74.200 + }
74.201 + }
74.202 +
74.203 + /// <summary>
74.204 + /// Gets the center point of the rectangle.
74.205 + /// </summary>
74.206 + /// <value>The center.</value>
74.207 + public ScreenPoint Center
74.208 + {
74.209 + get
74.210 + {
74.211 + return new ScreenPoint(this.left + (this.width * 0.5), this.top + (this.height * 0.5));
74.212 + }
74.213 + }
74.214 +
74.215 + /// <summary>
74.216 + /// Creates a rectangle from the specified corner coordinates.
74.217 + /// </summary>
74.218 + /// <param name="x0">
74.219 + /// The x0.
74.220 + /// </param>
74.221 + /// <param name="y0">
74.222 + /// The y0.
74.223 + /// </param>
74.224 + /// <param name="x1">
74.225 + /// The x1.
74.226 + /// </param>
74.227 + /// <param name="y1">
74.228 + /// The y1.
74.229 + /// </param>
74.230 + /// <returns>
74.231 + /// A rectangle.
74.232 + /// </returns>
74.233 + public static OxyRect Create(double x0, double y0, double x1, double y1)
74.234 + {
74.235 + return new OxyRect(Math.Min(x0, x1), Math.Min(y0, y1), Math.Abs(x1 - x0), Math.Abs(y1 - y0));
74.236 + }
74.237 +
74.238 + /// <summary>
74.239 + /// Creates a rectangle from the specified corner coordinates.
74.240 + /// </summary>
74.241 + /// <param name="p0">The first corner.</param>
74.242 + /// <param name="p1">The second corner.</param>
74.243 + /// <returns>A rectangle.</returns>
74.244 + public static OxyRect Create(ScreenPoint p0, ScreenPoint p1)
74.245 + {
74.246 + return Create(p0.X, p0.Y, p1.X, p1.Y);
74.247 + }
74.248 +
74.249 + /// <summary>
74.250 + /// Determines whether the specified point is inside the rectangle.
74.251 + /// </summary>
74.252 + /// <param name="x">
74.253 + /// The x coordinate.
74.254 + /// </param>
74.255 + /// <param name="y">
74.256 + /// The y coordinate.
74.257 + /// </param>
74.258 + /// <returns>
74.259 + /// <c>true</c> if the rectangle contains the specified point; otherwise, <c>false</c>.
74.260 + /// </returns>
74.261 + public bool Contains(double x, double y)
74.262 + {
74.263 + return x >= this.Left && x <= this.Right && y >= this.Top && y <= this.Bottom;
74.264 + }
74.265 +
74.266 + /// <summary>
74.267 + /// Determines whether the specified point is inside the rectangle.
74.268 + /// </summary>
74.269 + /// <param name="p">The point.</param>
74.270 + /// <returns>
74.271 + /// <c>true</c> if the rectangle contains the specified point; otherwise, <c>false</c>.
74.272 + /// </returns>
74.273 + public bool Contains(ScreenPoint p)
74.274 + {
74.275 + return this.Contains(p.x, p.y);
74.276 + }
74.277 +
74.278 + /// <summary>
74.279 + /// Returns a <see cref="System.String"/> that represents this instance.
74.280 + /// </summary>
74.281 + /// <returns>
74.282 + /// A <see cref="System.String"/> that represents this instance.
74.283 + /// </returns>
74.284 + public override string ToString()
74.285 + {
74.286 + return string.Format(
74.287 + CultureInfo.InvariantCulture, "({0}, {1}, {2}, {3})", this.left, this.top, this.width, this.height);
74.288 + }
74.289 + }
74.290 +}
74.291 \ No newline at end of file
75.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
75.2 +++ b/External/OxyPlot/OxyPlot/Foundation/OxySize.cs Sat Jun 08 16:53:22 2013 +0000
75.3 @@ -0,0 +1,87 @@
75.4 +// --------------------------------------------------------------------------------------------------------------------
75.5 +// <copyright file="OxySize.cs" company="OxyPlot">
75.6 +// The MIT License (MIT)
75.7 +//
75.8 +// Copyright (c) 2012 Oystein Bjorke
75.9 +//
75.10 +// Permission is hereby granted, free of charge, to any person obtaining a
75.11 +// copy of this software and associated documentation files (the
75.12 +// "Software"), to deal in the Software without restriction, including
75.13 +// without limitation the rights to use, copy, modify, merge, publish,
75.14 +// distribute, sublicense, and/or sell copies of the Software, and to
75.15 +// permit persons to whom the Software is furnished to do so, subject to
75.16 +// the following conditions:
75.17 +//
75.18 +// The above copyright notice and this permission notice shall be included
75.19 +// in all copies or substantial portions of the Software.
75.20 +//
75.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
75.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
75.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
75.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
75.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
75.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
75.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
75.28 +// </copyright>
75.29 +// <summary>
75.30 +// Implements a structure that is used to describe the Size of an object.
75.31 +// </summary>
75.32 +// --------------------------------------------------------------------------------------------------------------------
75.33 +namespace OxyPlot
75.34 +{
75.35 + using System.Globalization;
75.36 +
75.37 + /// <summary>
75.38 + /// Implements a structure that is used to describe the size of an object.
75.39 + /// </summary>
75.40 + public struct OxySize
75.41 + {
75.42 + /// <summary>
75.43 + /// Empty Size.
75.44 + /// </summary>
75.45 + public static OxySize Empty = new OxySize(0, 0);
75.46 +
75.47 + /// <summary>
75.48 + /// Initializes a new instance of the <see cref="OxySize"/> struct.
75.49 + /// </summary>
75.50 + /// <param name="width">
75.51 + /// The width.
75.52 + /// </param>
75.53 + /// <param name="height">
75.54 + /// The height.
75.55 + /// </param>
75.56 + public OxySize(double width, double height)
75.57 + : this()
75.58 + {
75.59 + this.Width = width;
75.60 + this.Height = height;
75.61 + }
75.62 +
75.63 + /// <summary>
75.64 + /// Gets or sets the height.
75.65 + /// </summary>
75.66 + /// <value>
75.67 + /// The height.
75.68 + /// </value>
75.69 + public double Height { get; set; }
75.70 +
75.71 + /// <summary>
75.72 + /// Gets or sets the width.
75.73 + /// </summary>
75.74 + /// <value>
75.75 + /// The width.
75.76 + /// </value>
75.77 + public double Width { get; set; }
75.78 +
75.79 + /// <summary>
75.80 + /// Returns a <see cref="System.String"/> that represents this instance.
75.81 + /// </summary>
75.82 + /// <returns>
75.83 + /// A <see cref="System.String"/> that represents this instance.
75.84 + /// </returns>
75.85 + public override string ToString()
75.86 + {
75.87 + return string.Format(CultureInfo.InvariantCulture, "({0}, {1})", this.Width, this.Height);
75.88 + }
75.89 + }
75.90 +}
75.91 \ No newline at end of file
76.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
76.2 +++ b/External/OxyPlot/OxyPlot/Foundation/OxyThickness.cs Sat Jun 08 16:53:22 2013 +0000
76.3 @@ -0,0 +1,220 @@
76.4 +// --------------------------------------------------------------------------------------------------------------------
76.5 +// <copyright file="OxyThickness.cs" company="OxyPlot">
76.6 +// The MIT License (MIT)
76.7 +//
76.8 +// Copyright (c) 2012 Oystein Bjorke
76.9 +//
76.10 +// Permission is hereby granted, free of charge, to any person obtaining a
76.11 +// copy of this software and associated documentation files (the
76.12 +// "Software"), to deal in the Software without restriction, including
76.13 +// without limitation the rights to use, copy, modify, merge, publish,
76.14 +// distribute, sublicense, and/or sell copies of the Software, and to
76.15 +// permit persons to whom the Software is furnished to do so, subject to
76.16 +// the following conditions:
76.17 +//
76.18 +// The above copyright notice and this permission notice shall be included
76.19 +// in all copies or substantial portions of the Software.
76.20 +//
76.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
76.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
76.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
76.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
76.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
76.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
76.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
76.28 +// </copyright>
76.29 +// <summary>
76.30 +// Describes the thickness of a frame around a rectangle. Four Double values describe the Left, Top, Right, and Bottom sides of the rectangle, respectively.
76.31 +// </summary>
76.32 +// --------------------------------------------------------------------------------------------------------------------
76.33 +namespace OxyPlot
76.34 +{
76.35 + using System.Globalization;
76.36 +
76.37 + /// <summary>
76.38 + /// Describes the thickness of a frame around a rectangle. Four <see cref="System.Double"/> values describe the left, top, right, and bottom sides of the rectangle, respectively.
76.39 + /// </summary>
76.40 + public struct OxyThickness : ICodeGenerating
76.41 + {
76.42 + /// <summary>
76.43 + /// The bottom.
76.44 + /// </summary>
76.45 + private double bottom;
76.46 +
76.47 + /// <summary>
76.48 + /// The left.
76.49 + /// </summary>
76.50 + private double left;
76.51 +
76.52 + /// <summary>
76.53 + /// The right.
76.54 + /// </summary>
76.55 + private double right;
76.56 +
76.57 + /// <summary>
76.58 + /// The top.
76.59 + /// </summary>
76.60 + private double top;
76.61 +
76.62 + /// <summary>
76.63 + /// Initializes a new instance of the <see cref="OxyThickness"/> struct.
76.64 + /// </summary>
76.65 + /// <param name="thickness">
76.66 + /// The thickness.
76.67 + /// </param>
76.68 + public OxyThickness(double thickness)
76.69 + : this(thickness, thickness, thickness, thickness)
76.70 + {
76.71 + }
76.72 +
76.73 + /// <summary>
76.74 + /// Initializes a new instance of the <see cref="OxyThickness"/> struct.
76.75 + /// </summary>
76.76 + /// <param name="left">
76.77 + /// The left.
76.78 + /// </param>
76.79 + /// <param name="top">
76.80 + /// The top.
76.81 + /// </param>
76.82 + /// <param name="right">
76.83 + /// The right.
76.84 + /// </param>
76.85 + /// <param name="bottom">
76.86 + /// The bottom.
76.87 + /// </param>
76.88 + public OxyThickness(double left, double top, double right, double bottom)
76.89 + {
76.90 + this.left = left;
76.91 + this.top = top;
76.92 + this.right = right;
76.93 + this.bottom = bottom;
76.94 + }
76.95 +
76.96 + /// <summary>
76.97 + /// Gets or sets the bottom thickness.
76.98 + /// </summary>
76.99 + /// <value>
76.100 + /// The bottom thickness.
76.101 + /// </value>
76.102 + public double Bottom
76.103 + {
76.104 + get
76.105 + {
76.106 + return this.bottom;
76.107 + }
76.108 +
76.109 + set
76.110 + {
76.111 + this.bottom = value;
76.112 + }
76.113 + }
76.114 +
76.115 + /// <summary>
76.116 + /// Gets the height.
76.117 + /// </summary>
76.118 + public double Height
76.119 + {
76.120 + get
76.121 + {
76.122 + return this.Bottom - this.Top;
76.123 + }
76.124 + }
76.125 +
76.126 + /// <summary>
76.127 + /// Gets or sets the left thickness.
76.128 + /// </summary>
76.129 + /// <value>
76.130 + /// The left thickness.
76.131 + /// </value>
76.132 + public double Left
76.133 + {
76.134 + get
76.135 + {
76.136 + return this.left;
76.137 + }
76.138 +
76.139 + set
76.140 + {
76.141 + this.left = value;
76.142 + }
76.143 + }
76.144 +
76.145 + /// <summary>
76.146 + /// Gets or sets the right thickness.
76.147 + /// </summary>
76.148 + /// <value>
76.149 + /// The right thickness.
76.150 + /// </value>
76.151 + public double Right
76.152 + {
76.153 + get
76.154 + {
76.155 + return this.right;
76.156 + }
76.157 +
76.158 + set
76.159 + {
76.160 + this.right = value;
76.161 + }
76.162 + }
76.163 +
76.164 + /// <summary>
76.165 + /// Gets or sets the top thickness.
76.166 + /// </summary>
76.167 + /// <value>
76.168 + /// The top thickness.
76.169 + /// </value>
76.170 + public double Top
76.171 + {
76.172 + get
76.173 + {
76.174 + return this.top;
76.175 + }
76.176 +
76.177 + set
76.178 + {
76.179 + this.top = value;
76.180 + }
76.181 + }
76.182 +
76.183 + /// <summary>
76.184 + /// Gets the width.
76.185 + /// </summary>
76.186 + public double Width
76.187 + {
76.188 + get
76.189 + {
76.190 + return this.Right - this.Left;
76.191 + }
76.192 + }
76.193 +
76.194 + /// <summary>
76.195 + /// Returns C# code that generates this instance.
76.196 + /// </summary>
76.197 + /// <returns>
76.198 + /// The to code.
76.199 + /// </returns>
76.200 + public string ToCode()
76.201 + {
76.202 + return string.Format(
76.203 + CultureInfo.InvariantCulture,
76.204 + "new OxyThickness({0},{1},{2},{3})",
76.205 + this.Left,
76.206 + this.Top,
76.207 + this.Right,
76.208 + this.Bottom);
76.209 + }
76.210 +
76.211 + /// <summary>
76.212 + /// Returns a <see cref="System.String"/> that represents this instance.
76.213 + /// </summary>
76.214 + /// <returns>
76.215 + /// A <see cref="System.String"/> that represents this instance.
76.216 + /// </returns>
76.217 + public override string ToString()
76.218 + {
76.219 + return string.Format(
76.220 + CultureInfo.InvariantCulture, "({0}, {1}, {2}, {3})", this.left, this.top, this.right, this.bottom);
76.221 + }
76.222 + }
76.223 +}
76.224 \ No newline at end of file
77.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
77.2 +++ b/External/OxyPlot/OxyPlot/Foundation/Pen.cs Sat Jun 08 16:53:22 2013 +0000
77.3 @@ -0,0 +1,42 @@
77.4 +// --------------------------------------------------------------------------------------------------------------------
77.5 +// <copyright file="Pen.cs" company="OxyPlot">
77.6 +// The MIT License (MIT)
77.7 +//
77.8 +// Copyright (c) 2012 Oystein Bjorke
77.9 +//
77.10 +// Permission is hereby granted, free of charge, to any person obtaining a
77.11 +// copy of this software and associated documentation files (the
77.12 +// "Software"), to deal in the Software without restriction, including
77.13 +// without limitation the rights to use, copy, modify, merge, publish,
77.14 +// distribute, sublicense, and/or sell copies of the Software, and to
77.15 +// permit persons to whom the Software is furnished to do so, subject to
77.16 +// the following conditions:
77.17 +//
77.18 +// The above copyright notice and this permission notice shall be included
77.19 +// in all copies or substantial portions of the Software.
77.20 +//
77.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
77.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
77.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
77.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
77.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
77.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
77.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
77.28 +// </copyright>
77.29 +// --------------------------------------------------------------------------------------------------------------------
77.30 +namespace OxyPlot
77.31 +{
77.32 + public class Pen
77.33 + {
77.34 + public Pen(Color c, double th, LineStyle ls)
77.35 + {
77.36 + Color = c;
77.37 + Thickness = th;
77.38 + DashArray = LineStyleHelper.GetDashArray(ls);
77.39 + }
77.40 +
77.41 + public Color Color { get; set; }
77.42 + public double Thickness { get; set; }
77.43 + public double[] DashArray { get; set; }
77.44 + }
77.45 +}
77.46 \ No newline at end of file
78.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
78.2 +++ b/External/OxyPlot/OxyPlot/Foundation/PlotLength.cs Sat Jun 08 16:53:22 2013 +0000
78.3 @@ -0,0 +1,91 @@
78.4 +// --------------------------------------------------------------------------------------------------------------------
78.5 +// <copyright file="PlotLength.cs" company="OxyPlot">
78.6 +// The MIT License (MIT)
78.7 +//
78.8 +// Copyright (c) 2012 Oystein Bjorke
78.9 +//
78.10 +// Permission is hereby granted, free of charge, to any person obtaining a
78.11 +// copy of this software and associated documentation files (the
78.12 +// "Software"), to deal in the Software without restriction, including
78.13 +// without limitation the rights to use, copy, modify, merge, publish,
78.14 +// distribute, sublicense, and/or sell copies of the Software, and to
78.15 +// permit persons to whom the Software is furnished to do so, subject to
78.16 +// the following conditions:
78.17 +//
78.18 +// The above copyright notice and this permission notice shall be included
78.19 +// in all copies or substantial portions of the Software.
78.20 +//
78.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
78.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
78.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
78.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
78.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
78.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
78.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
78.28 +// </copyright>
78.29 +// <summary>
78.30 +// Represents lengths in the plot.
78.31 +// </summary>
78.32 +// --------------------------------------------------------------------------------------------------------------------
78.33 +
78.34 +namespace OxyPlot
78.35 +{
78.36 + /// <summary>
78.37 + /// Represents lengths in the plot.
78.38 + /// </summary>
78.39 + public struct PlotLength
78.40 + {
78.41 + /// <summary>
78.42 + /// The unit type
78.43 + /// </summary>
78.44 + private readonly PlotLengthUnit unit;
78.45 +
78.46 + /// <summary>
78.47 + /// The value
78.48 + /// </summary>
78.49 + private readonly double value;
78.50 +
78.51 + /// <summary>
78.52 + /// Initializes a new instance of the <see cref="PlotLength"/> struct.
78.53 + /// </summary>
78.54 + /// <param name="value">
78.55 + /// The value.
78.56 + /// </param>
78.57 + /// <param name="unit">
78.58 + /// The unit.
78.59 + /// </param>
78.60 + public PlotLength(double value, PlotLengthUnit unit)
78.61 + {
78.62 + this.value = value;
78.63 + this.unit = unit;
78.64 + }
78.65 +
78.66 + /// <summary>
78.67 + /// Gets the value.
78.68 + /// </summary>
78.69 + /// <value>
78.70 + /// The value.
78.71 + /// </value>
78.72 + public double Value
78.73 + {
78.74 + get
78.75 + {
78.76 + return this.value;
78.77 + }
78.78 + }
78.79 +
78.80 + /// <summary>
78.81 + /// Gets the type of the unit.
78.82 + /// </summary>
78.83 + /// <value>
78.84 + /// The type of the unit.
78.85 + /// </value>
78.86 + public PlotLengthUnit Unit
78.87 + {
78.88 + get
78.89 + {
78.90 + return this.unit;
78.91 + }
78.92 + }
78.93 + }
78.94 +}
78.95 \ No newline at end of file
79.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
79.2 +++ b/External/OxyPlot/OxyPlot/Foundation/PlotLengthUnit.cs Sat Jun 08 16:53:22 2013 +0000
79.3 @@ -0,0 +1,58 @@
79.4 +// --------------------------------------------------------------------------------------------------------------------
79.5 +// <copyright file="PlotLengthUnit.cs" company="OxyPlot">
79.6 +// The MIT License (MIT)
79.7 +//
79.8 +// Copyright (c) 2012 Oystein Bjorke
79.9 +//
79.10 +// Permission is hereby granted, free of charge, to any person obtaining a
79.11 +// copy of this software and associated documentation files (the
79.12 +// "Software"), to deal in the Software without restriction, including
79.13 +// without limitation the rights to use, copy, modify, merge, publish,
79.14 +// distribute, sublicense, and/or sell copies of the Software, and to
79.15 +// permit persons to whom the Software is furnished to do so, subject to
79.16 +// the following conditions:
79.17 +//
79.18 +// The above copyright notice and this permission notice shall be included
79.19 +// in all copies or substantial portions of the Software.
79.20 +//
79.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
79.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
79.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
79.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
79.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
79.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
79.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
79.28 +// </copyright>
79.29 +// <summary>
79.30 +// Describes the kind of value that a <see cref="PlotLength" /> object is holding.
79.31 +// </summary>
79.32 +// --------------------------------------------------------------------------------------------------------------------
79.33 +
79.34 +namespace OxyPlot
79.35 +{
79.36 + /// <summary>
79.37 + /// Describes the kind of value that a <see cref="PlotLength"/> object is holding.
79.38 + /// </summary>
79.39 + public enum PlotLengthUnit
79.40 + {
79.41 + /// <summary>
79.42 + /// The value is in data space (transformed by x/y axis)
79.43 + /// </summary>
79.44 + Data = 0,
79.45 +
79.46 + /// <summary>
79.47 + /// The value is in screen units
79.48 + /// </summary>
79.49 + ScreenUnits = 1,
79.50 +
79.51 + /// <summary>
79.52 + /// The value is relative to the plot viewport (0-1)
79.53 + /// </summary>
79.54 + RelativeToViewport = 2,
79.55 +
79.56 + /// <summary>
79.57 + /// The value is relative to the plot area (0-1)
79.58 + /// </summary>
79.59 + RelativeToPlotArea = 3
79.60 + }
79.61 +}
79.62 \ No newline at end of file
80.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
80.2 +++ b/External/OxyPlot/OxyPlot/Foundation/PngEncoder.cs Sat Jun 08 16:53:22 2013 +0000
80.3 @@ -0,0 +1,323 @@
80.4 +// --------------------------------------------------------------------------------------------------------------------
80.5 +// <copyright file="PngEncoder.cs" company="OxyPlot">
80.6 +// The MIT License (MIT)
80.7 +//
80.8 +// Copyright (c) 2012 Oystein Bjorke
80.9 +//
80.10 +// Permission is hereby granted, free of charge, to any person obtaining a
80.11 +// copy of this software and associated documentation files (the
80.12 +// "Software"), to deal in the Software without restriction, including
80.13 +// without limitation the rights to use, copy, modify, merge, publish,
80.14 +// distribute, sublicense, and/or sell copies of the Software, and to
80.15 +// permit persons to whom the Software is furnished to do so, subject to
80.16 +// the following conditions:
80.17 +//
80.18 +// The above copyright notice and this permission notice shall be included
80.19 +// in all copies or substantial portions of the Software.
80.20 +//
80.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
80.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
80.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
80.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
80.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
80.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
80.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
80.28 +// </copyright>
80.29 +// --------------------------------------------------------------------------------------------------------------------
80.30 +
80.31 +namespace OxyPlot
80.32 +{
80.33 + using System;
80.34 + using System.Collections.Generic;
80.35 + using System.IO;
80.36 + using System.Linq;
80.37 +
80.38 + /// <summary>
80.39 + /// Provides encoding of uncompressed png images.
80.40 + /// </summary>
80.41 + public class PngEncoder
80.42 + {
80.43 + /// <summary>
80.44 + /// The CRC table
80.45 + /// </summary>
80.46 + private static readonly ulong[] CrcTable;
80.47 +
80.48 + /// <summary>
80.49 + /// Initializes static members of the <see cref="PngEncoder" /> class.
80.50 + /// </summary>
80.51 + static PngEncoder()
80.52 + {
80.53 + CrcTable = new ulong[256];
80.54 + for (int n = 0; n < 256; n++)
80.55 + {
80.56 + var c = (ulong)n;
80.57 + for (int k = 0; k < 8; k++)
80.58 + {
80.59 + if ((c & 1) != 0)
80.60 + {
80.61 + c = 0xedb88320L ^ (c >> 1);
80.62 + }
80.63 + else
80.64 + {
80.65 + c = c >> 1;
80.66 + }
80.67 + }
80.68 +
80.69 + CrcTable[n] = c;
80.70 + }
80.71 + }
80.72 +
80.73 + /// <summary>
80.74 + /// Encodes the specified image data to png.
80.75 + /// </summary>
80.76 + /// <param name="pixels">
80.77 + /// The pixel data (bottom line first).
80.78 + /// </param>
80.79 + /// <param name="dpi">
80.80 + /// The image resolution in dots per inch.
80.81 + /// </param>
80.82 + /// <returns>
80.83 + /// The png image data.
80.84 + /// </returns>
80.85 + public static byte[] Encode(OxyColor[,] pixels, int dpi = 96)
80.86 + {
80.87 + int height = pixels.GetLength(0);
80.88 + int width = pixels.GetLength(1);
80.89 + var bytes = new byte[(width * height * 4) + height];
80.90 +
80.91 + int k = 0;
80.92 + for (int i = height - 1; i >= 0; i--)
80.93 + {
80.94 + bytes[k++] = 0; // Filter
80.95 + for (int j = 0; j < width; j++)
80.96 + {
80.97 + bytes[k++] = pixels[i, j].R;
80.98 + bytes[k++] = pixels[i, j].G;
80.99 + bytes[k++] = pixels[i, j].B;
80.100 + bytes[k++] = pixels[i, j].A;
80.101 + }
80.102 + }
80.103 +
80.104 + var w = new MemoryWriter();
80.105 + w.Write((byte)0x89);
80.106 + w.Write("PNG\r\n\x1a\n".ToCharArray());
80.107 + WriteChunk(w, "IHDR", CreateHeaderData(width, height));
80.108 + WriteChunk(w, "pHYs", CreatePhysicalDimensionsData(dpi, dpi));
80.109 + WriteChunk(w, "IDAT", CreateUncompressedBlocks(bytes));
80.110 + WriteChunk(w, "IEND", new byte[0]);
80.111 + return w.ToArray();
80.112 + }
80.113 +
80.114 + /// <summary>
80.115 + /// Calculates the Adler-32 check sum.
80.116 + /// </summary>
80.117 + /// <param name="data">
80.118 + /// The data.
80.119 + /// </param>
80.120 + /// <returns>
80.121 + /// The check sum.
80.122 + /// </returns>
80.123 + private static uint Adler32(IEnumerable<byte> data)
80.124 + {
80.125 + // http://en.wikipedia.org/wiki/Adler-32
80.126 + uint a = 1;
80.127 + uint b = 0;
80.128 + const uint ModAdler = 65521;
80.129 + foreach (var x in data)
80.130 + {
80.131 + a = (a + x) % ModAdler;
80.132 + b = (b + a) % ModAdler;
80.133 + }
80.134 +
80.135 + return (b << 16) | a;
80.136 + }
80.137 +
80.138 + /// <summary>
80.139 + /// Creates the header data.
80.140 + /// </summary>
80.141 + /// <param name="width">
80.142 + /// The width.
80.143 + /// </param>
80.144 + /// <param name="height">
80.145 + /// The height.
80.146 + /// </param>
80.147 + /// <returns>
80.148 + /// The header.
80.149 + /// </returns>
80.150 + private static byte[] CreateHeaderData(int width, int height)
80.151 + {
80.152 + // http://www.w3.org/TR/PNG-Chunks.html
80.153 + var w = new MemoryWriter();
80.154 + WriteBigEndian(w, width);
80.155 + WriteBigEndian(w, height);
80.156 + w.Write((byte)8); // bit depth
80.157 + w.Write((byte)6); // color type RGBA
80.158 + w.Write((byte)0); // compression method
80.159 + w.Write((byte)0); // filter method
80.160 + w.Write((byte)0); // interlace method
80.161 + return w.ToArray();
80.162 + }
80.163 +
80.164 + /// <summary>
80.165 + /// Creates the physical dimensions data.
80.166 + /// </summary>
80.167 + /// <param name="dpix">
80.168 + /// The horizontal resolution.
80.169 + /// </param>
80.170 + /// <param name="dpiy">
80.171 + /// The vertical resolution.
80.172 + /// </param>
80.173 + /// <returns>
80.174 + /// The data.
80.175 + /// </returns>
80.176 + private static byte[] CreatePhysicalDimensionsData(int dpix, int dpiy)
80.177 + {
80.178 + var ppux = (int)(dpix / 0.0254);
80.179 + var ppuy = (int)(dpiy / 0.0254);
80.180 + var w = new MemoryWriter();
80.181 + WriteBigEndian(w, ppux);
80.182 + WriteBigEndian(w, ppuy);
80.183 + w.Write((byte)1); // Unit: metre
80.184 + return w.ToArray();
80.185 + }
80.186 +
80.187 + /// <summary>
80.188 + /// Creates the uncompressed blocks.
80.189 + /// </summary>
80.190 + /// <param name="bytes">
80.191 + /// The data.
80.192 + /// </param>
80.193 + /// <returns>
80.194 + /// The output data.
80.195 + /// </returns>
80.196 + private static byte[] CreateUncompressedBlocks(byte[] bytes)
80.197 + {
80.198 + // http://www.w3.org/TR/PNG-Compression.html
80.199 + const int MaxDeflate = 0xFFFF;
80.200 + var w = new MemoryWriter();
80.201 + const uint CompressionMethod = 8;
80.202 + const uint Check = (31 - ((CompressionMethod << 8) % 31)) % 31;
80.203 + w.Write((byte)CompressionMethod);
80.204 + w.Write((byte)Check);
80.205 + for (int i = 0; i < bytes.Length; i += MaxDeflate)
80.206 + {
80.207 + var n = (ushort)Math.Min(bytes.Length - i, MaxDeflate);
80.208 + var last = (byte)(i + n < bytes.Length ? 0 : 1);
80.209 + w.Write(last);
80.210 + w.Write((byte)(n & 0xFF));
80.211 + w.Write((byte)((n >> 8) & 0xFF));
80.212 + var n2 = ~n;
80.213 + w.Write((byte)(n2 & 0xFF));
80.214 + w.Write((byte)((n2 >> 8) & 0xFF));
80.215 + w.Write(bytes, i, n);
80.216 + }
80.217 +
80.218 + WriteBigEndian(w, Adler32(bytes));
80.219 + return w.ToArray();
80.220 + }
80.221 +
80.222 + /// <summary>
80.223 + /// Updates the CRC check sum.
80.224 + /// </summary>
80.225 + /// <param name="crc">
80.226 + /// The input CRC.
80.227 + /// </param>
80.228 + /// <param name="data">
80.229 + /// The data.
80.230 + /// </param>
80.231 + /// <returns>
80.232 + /// The updated CRC.
80.233 + /// </returns>
80.234 + private static ulong UpdateCrc(ulong crc, IEnumerable<byte> data)
80.235 + {
80.236 + return data.Aggregate(crc, (current, x) => CrcTable[(current ^ x) & 0xff] ^ (current >> 8));
80.237 + }
80.238 +
80.239 + /// <summary>
80.240 + /// Writes the integer value with big endian byte order.
80.241 + /// </summary>
80.242 + /// <param name="w">
80.243 + /// The writer.
80.244 + /// </param>
80.245 + /// <param name="value">
80.246 + /// The value.
80.247 + /// </param>
80.248 + private static void WriteBigEndian(BinaryWriter w, int value)
80.249 + {
80.250 + var bytes = BitConverter.GetBytes(value);
80.251 + w.Write(bytes[3]);
80.252 + w.Write(bytes[2]);
80.253 + w.Write(bytes[1]);
80.254 + w.Write(bytes[0]);
80.255 + }
80.256 +
80.257 + /// <summary>
80.258 + /// Writes the unsigned integer value with big endian byte order.
80.259 + /// </summary>
80.260 + /// <param name="w">
80.261 + /// The writer.
80.262 + /// </param>
80.263 + /// <param name="value">
80.264 + /// The value.
80.265 + /// </param>
80.266 + private static void WriteBigEndian(BinaryWriter w, uint value)
80.267 + {
80.268 + var bytes = BitConverter.GetBytes(value);
80.269 + w.Write(bytes[3]);
80.270 + w.Write(bytes[2]);
80.271 + w.Write(bytes[1]);
80.272 + w.Write(bytes[0]);
80.273 + }
80.274 +
80.275 + /// <summary>
80.276 + /// Writes a png chunk.
80.277 + /// </summary>
80.278 + /// <param name="w">
80.279 + /// The writer.
80.280 + /// </param>
80.281 + /// <param name="type">
80.282 + /// The chunk type.
80.283 + /// </param>
80.284 + /// <param name="data">
80.285 + /// The chunk data.
80.286 + /// </param>
80.287 + private static void WriteChunk(BinaryWriter w, string type, byte[] data)
80.288 + {
80.289 + var ty = type.ToCharArray().Select(ch => (byte)ch).ToArray();
80.290 + WriteBigEndian(w, data.Length);
80.291 + w.Write(ty);
80.292 + w.Write(data);
80.293 +
80.294 + var c = 0xffffffff;
80.295 + c = (uint)UpdateCrc(c, ty);
80.296 + c = (uint)UpdateCrc(c, data);
80.297 + var crc = c ^ 0xffffffff;
80.298 +
80.299 + WriteBigEndian(w, crc);
80.300 + }
80.301 +
80.302 + /// <summary>
80.303 + /// Provides a binary writer that writes to memory.
80.304 + /// </summary>
80.305 + private class MemoryWriter : BinaryWriter
80.306 + {
80.307 + /// <summary>
80.308 + /// Initializes a new instance of the <see cref="MemoryWriter" /> class.
80.309 + /// </summary>
80.310 + public MemoryWriter()
80.311 + : base(new MemoryStream())
80.312 + {
80.313 + }
80.314 +
80.315 + /// <summary>
80.316 + /// Gets the content as a byte array.
80.317 + /// </summary>
80.318 + /// <returns>The byte array.</returns>
80.319 + public byte[] ToArray()
80.320 + {
80.321 + this.BaseStream.Flush();
80.322 + return ((MemoryStream)this.BaseStream).ToArray();
80.323 + }
80.324 + }
80.325 + }
80.326 +}
80.327 \ No newline at end of file
81.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
81.2 +++ b/External/OxyPlot/OxyPlot/Foundation/Point.cs Sat Jun 08 16:53:22 2013 +0000
81.3 @@ -0,0 +1,58 @@
81.4 +// --------------------------------------------------------------------------------------------------------------------
81.5 +// <copyright file="Point.cs" company="OxyPlot">
81.6 +// The MIT License (MIT)
81.7 +//
81.8 +// Copyright (c) 2012 Oystein Bjorke
81.9 +//
81.10 +// Permission is hereby granted, free of charge, to any person obtaining a
81.11 +// copy of this software and associated documentation files (the
81.12 +// "Software"), to deal in the Software without restriction, including
81.13 +// without limitation the rights to use, copy, modify, merge, publish,
81.14 +// distribute, sublicense, and/or sell copies of the Software, and to
81.15 +// permit persons to whom the Software is furnished to do so, subject to
81.16 +// the following conditions:
81.17 +//
81.18 +// The above copyright notice and this permission notice shall be included
81.19 +// in all copies or substantial portions of the Software.
81.20 +//
81.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
81.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
81.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
81.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
81.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
81.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
81.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
81.28 +// </copyright>
81.29 +// --------------------------------------------------------------------------------------------------------------------
81.30 +namespace OxyPlot
81.31 +{
81.32 + public struct Point
81.33 + {
81.34 + internal double x;
81.35 +
81.36 + internal double y;
81.37 +
81.38 + public Point(double x, double y)
81.39 + {
81.40 + this.x = x;
81.41 + this.y = y;
81.42 + }
81.43 +
81.44 + public double X
81.45 + {
81.46 + get { return x; }
81.47 + set { x = value; }
81.48 + }
81.49 +
81.50 + public double Y
81.51 + {
81.52 + get { return y; }
81.53 + set { y = value; }
81.54 + }
81.55 +
81.56 + public override string ToString()
81.57 + {
81.58 + return x + " " + y;
81.59 + }
81.60 + }
81.61 +}
81.62 \ No newline at end of file
82.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
82.2 +++ b/External/OxyPlot/OxyPlot/Foundation/Rectangle.cs Sat Jun 08 16:53:22 2013 +0000
82.3 @@ -0,0 +1,36 @@
82.4 +// --------------------------------------------------------------------------------------------------------------------
82.5 +// <copyright file="Rectangle.cs" company="OxyPlot">
82.6 +// The MIT License (MIT)
82.7 +//
82.8 +// Copyright (c) 2012 Oystein Bjorke
82.9 +//
82.10 +// Permission is hereby granted, free of charge, to any person obtaining a
82.11 +// copy of this software and associated documentation files (the
82.12 +// "Software"), to deal in the Software without restriction, including
82.13 +// without limitation the rights to use, copy, modify, merge, publish,
82.14 +// distribute, sublicense, and/or sell copies of the Software, and to
82.15 +// permit persons to whom the Software is furnished to do so, subject to
82.16 +// the following conditions:
82.17 +//
82.18 +// The above copyright notice and this permission notice shall be included
82.19 +// in all copies or substantial portions of the Software.
82.20 +//
82.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
82.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
82.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
82.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
82.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
82.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
82.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
82.28 +// </copyright>
82.29 +// --------------------------------------------------------------------------------------------------------------------
82.30 +namespace OxyPlot
82.31 +{
82.32 + public struct Rectangle
82.33 + {
82.34 + public double Top { get; set; }
82.35 + public double Bottom { get; set; }
82.36 + public double Left { get; set; }
82.37 + public double Right { get; set; }
82.38 + }
82.39 +}
82.40 \ No newline at end of file
83.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
83.2 +++ b/External/OxyPlot/OxyPlot/Foundation/ReflectionHelper.cs Sat Jun 08 16:53:22 2013 +0000
83.3 @@ -0,0 +1,81 @@
83.4 +// --------------------------------------------------------------------------------------------------------------------
83.5 +// <copyright file="ReflectionHelper.cs" company="OxyPlot">
83.6 +// The MIT License (MIT)
83.7 +//
83.8 +// Copyright (c) 2012 Oystein Bjorke
83.9 +//
83.10 +// Permission is hereby granted, free of charge, to any person obtaining a
83.11 +// copy of this software and associated documentation files (the
83.12 +// "Software"), to deal in the Software without restriction, including
83.13 +// without limitation the rights to use, copy, modify, merge, publish,
83.14 +// distribute, sublicense, and/or sell copies of the Software, and to
83.15 +// permit persons to whom the Software is furnished to do so, subject to
83.16 +// the following conditions:
83.17 +//
83.18 +// The above copyright notice and this permission notice shall be included
83.19 +// in all copies or substantial portions of the Software.
83.20 +//
83.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
83.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
83.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
83.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
83.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
83.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
83.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
83.28 +// </copyright>
83.29 +// <summary>
83.30 +// Provides reflection based support methods.
83.31 +// </summary>
83.32 +// --------------------------------------------------------------------------------------------------------------------
83.33 +namespace OxyPlot
83.34 +{
83.35 + using System;
83.36 + using System.Collections;
83.37 + using System.Collections.Generic;
83.38 + using System.Globalization;
83.39 + using System.Reflection;
83.40 +
83.41 + /// <summary>
83.42 + /// Provides utility methods reflection based support methods.
83.43 + /// </summary>
83.44 + public static class ReflectionHelper
83.45 + {
83.46 + /// <summary>
83.47 + /// Fills a list by the specified property of a source list/enumerable.
83.48 + /// </summary>
83.49 + /// <param name="source">
83.50 + /// The source list.
83.51 + /// </param>
83.52 + /// <param name="propertyName">
83.53 + /// The property name.
83.54 + /// </param>
83.55 + /// <param name="list">
83.56 + /// The list to be filled.
83.57 + /// </param>
83.58 + /// <typeparam name="T">
83.59 + /// The type of the destination list items (and the source property).
83.60 + /// </typeparam>
83.61 + public static void FillList<T>(IEnumerable source, string propertyName, IList<T> list)
83.62 + {
83.63 + PropertyInfo pi = null;
83.64 + Type t = null;
83.65 + foreach (var o in source)
83.66 + {
83.67 + if (pi == null || o.GetType() != t)
83.68 + {
83.69 + t = o.GetType();
83.70 + pi = t.GetProperty(propertyName);
83.71 + if (pi == null)
83.72 + {
83.73 + throw new InvalidOperationException(
83.74 + string.Format("Could not find field {0} on type {1}", propertyName, t));
83.75 + }
83.76 + }
83.77 +
83.78 + var v = pi.GetValue(o, null);
83.79 + var value = (T)Convert.ChangeType(v, typeof(T), CultureInfo.InvariantCulture);
83.80 + list.Add(value);
83.81 + }
83.82 + }
83.83 + }
83.84 +}
83.85 \ No newline at end of file
84.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
84.2 +++ b/External/OxyPlot/OxyPlot/Foundation/ScreenPoint.cs Sat Jun 08 16:53:22 2013 +0000
84.3 @@ -0,0 +1,198 @@
84.4 +// --------------------------------------------------------------------------------------------------------------------
84.5 +// <copyright file="ScreenPoint.cs" company="OxyPlot">
84.6 +// The MIT License (MIT)
84.7 +//
84.8 +// Copyright (c) 2012 Oystein Bjorke
84.9 +//
84.10 +// Permission is hereby granted, free of charge, to any person obtaining a
84.11 +// copy of this software and associated documentation files (the
84.12 +// "Software"), to deal in the Software without restriction, including
84.13 +// without limitation the rights to use, copy, modify, merge, publish,
84.14 +// distribute, sublicense, and/or sell copies of the Software, and to
84.15 +// permit persons to whom the Software is furnished to do so, subject to
84.16 +// the following conditions:
84.17 +//
84.18 +// The above copyright notice and this permission notice shall be included
84.19 +// in all copies or substantial portions of the Software.
84.20 +//
84.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
84.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
84.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
84.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
84.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
84.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
84.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
84.28 +// </copyright>
84.29 +// <summary>
84.30 +// Describes a point defined in the screen coordinate system.
84.31 +// </summary>
84.32 +// --------------------------------------------------------------------------------------------------------------------
84.33 +namespace OxyPlot
84.34 +{
84.35 + using System;
84.36 +
84.37 + /// <summary>
84.38 + /// Represents a point defined in the screen coordinate system.
84.39 + /// </summary>
84.40 + /// <remarks>
84.41 + /// The rendering methods transforms <see cref="DataPoint"/>s to <see cref="ScreenPoint"/>s.
84.42 + /// </remarks>
84.43 + public struct ScreenPoint
84.44 + {
84.45 + /// <summary>
84.46 + /// The undefined point.
84.47 + /// </summary>
84.48 + public static readonly ScreenPoint Undefined = new ScreenPoint(double.NaN, double.NaN);
84.49 +
84.50 + /// <summary>
84.51 + /// The x-coordinate.
84.52 + /// </summary>
84.53 + internal double x;
84.54 +
84.55 + /// <summary>
84.56 + /// The y-coordinate.
84.57 + /// </summary>
84.58 + internal double y;
84.59 +
84.60 + /// <summary>
84.61 + /// Initializes a new instance of the <see cref="ScreenPoint"/> struct.
84.62 + /// </summary>
84.63 + /// <param name="x">
84.64 + /// The x-coordinate.
84.65 + /// </param>
84.66 + /// <param name="y">
84.67 + /// The y-coordinate.
84.68 + /// </param>
84.69 + public ScreenPoint(double x, double y)
84.70 + {
84.71 + this.x = x;
84.72 + this.y = y;
84.73 + }
84.74 +
84.75 + /// <summary>
84.76 + /// Gets or sets the x-coordinate.
84.77 + /// </summary>
84.78 + /// <value> The x-coordinate. </value>
84.79 + public double X
84.80 + {
84.81 + get
84.82 + {
84.83 + return this.x;
84.84 + }
84.85 +
84.86 + set
84.87 + {
84.88 + this.x = value;
84.89 + }
84.90 + }
84.91 +
84.92 + /// <summary>
84.93 + /// Gets or sets the y-coordinate.
84.94 + /// </summary>
84.95 + /// <value> The y-coordinate. </value>
84.96 + public double Y
84.97 + {
84.98 + get
84.99 + {
84.100 + return this.y;
84.101 + }
84.102 +
84.103 + set
84.104 + {
84.105 + this.y = value;
84.106 + }
84.107 + }
84.108 +
84.109 + /// <summary>
84.110 + /// Determines whether the specified point is undefined.
84.111 + /// </summary>
84.112 + /// <param name="point">
84.113 + /// The point.
84.114 + /// </param>
84.115 + /// <returns>
84.116 + /// <c>true</c> if the specified point is undefined; otherwise, <c>false</c> .
84.117 + /// </returns>
84.118 + public static bool IsUndefined(ScreenPoint point)
84.119 + {
84.120 + return double.IsNaN(point.X) && double.IsNaN(point.Y);
84.121 + }
84.122 +
84.123 + /// <summary>
84.124 + /// Gets the distance to the specified point.
84.125 + /// </summary>
84.126 + /// <param name="point">
84.127 + /// The point.
84.128 + /// </param>
84.129 + /// <returns>
84.130 + /// The distance.
84.131 + /// </returns>
84.132 + public double DistanceTo(ScreenPoint point)
84.133 + {
84.134 + double dx = point.x - this.x;
84.135 + double dy = point.y - this.y;
84.136 + return Math.Sqrt((dx * dx) + (dy * dy));
84.137 + }
84.138 +
84.139 + /// <summary>
84.140 + /// Gets the squared distance to the specified point.
84.141 + /// </summary>
84.142 + /// <param name="point">
84.143 + /// The point.
84.144 + /// </param>
84.145 + /// <returns>
84.146 + /// The squared distance.
84.147 + /// </returns>
84.148 + public double DistanceToSquared(ScreenPoint point)
84.149 + {
84.150 + double dx = point.x - this.x;
84.151 + double dy = point.y - this.y;
84.152 + return (dx * dx) + (dy * dy);
84.153 + }
84.154 +
84.155 + /// <summary>
84.156 + /// Returns a <see cref="System.String"/> that represents this instance.
84.157 + /// </summary>
84.158 + /// <returns>
84.159 + /// A <see cref="System.String"/> that represents this instance.
84.160 + /// </returns>
84.161 + public override string ToString()
84.162 + {
84.163 + return this.x + " " + this.y;
84.164 + }
84.165 +
84.166 + /// <summary>
84.167 + /// Translates a <see cref="ScreenPoint"/> by a <see cref="ScreenVector"/>.
84.168 + /// </summary>
84.169 + /// <param name="p1"> The point. </param>
84.170 + /// <param name="p2"> The vector. </param>
84.171 + /// <returns> The translated point. </returns>
84.172 + public static ScreenPoint operator +(ScreenPoint p1, ScreenVector p2)
84.173 + {
84.174 + return new ScreenPoint(p1.x + p2.x, p1.y + p2.y);
84.175 + }
84.176 +
84.177 + /// <summary>
84.178 + /// Subtracts a <see cref="ScreenPoint"/> from a <see cref="ScreenPoint"/>
84.179 + /// and returns the result as a <see cref="ScreenVector"/>.
84.180 + /// </summary>
84.181 + /// <param name="p1"> The point on which to perform the subtraction. </param>
84.182 + /// <param name="p2"> The point to subtract from p1. </param>
84.183 + /// <returns> A <see cref="ScreenVector"/> structure that represents the difference between p1 and p2. </returns>
84.184 + public static ScreenVector operator -(ScreenPoint p1, ScreenPoint p2)
84.185 + {
84.186 + return new ScreenVector(p1.x - p2.x, p1.y - p2.y);
84.187 + }
84.188 +
84.189 + /// <summary>
84.190 + /// Subtracts a <see cref="ScreenVector"/> from a <see cref="ScreenPoint"/>
84.191 + /// and returns the result as a <see cref="ScreenPoint"/>.
84.192 + /// </summary>
84.193 + /// <param name="point"> The point on which to perform the subtraction. </param>
84.194 + /// <param name="vector"> The vector to subtract from p1. </param>
84.195 + /// <returns> A <see cref="ScreenPoint"/> that represents point translated by the negative vector. </returns>
84.196 + public static ScreenPoint operator -(ScreenPoint point, ScreenVector vector)
84.197 + {
84.198 + return new ScreenPoint(point.x - vector.x, point.y - vector.y);
84.199 + }
84.200 + }
84.201 +}
84.202 \ No newline at end of file
85.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
85.2 +++ b/External/OxyPlot/OxyPlot/Foundation/ScreenPointHelper.cs Sat Jun 08 16:53:22 2013 +0000
85.3 @@ -0,0 +1,255 @@
85.4 +// --------------------------------------------------------------------------------------------------------------------
85.5 +// <copyright file="ScreenPointHelper.cs" company="OxyPlot">
85.6 +// The MIT License (MIT)
85.7 +//
85.8 +// Copyright (c) 2012 Oystein Bjorke
85.9 +//
85.10 +// Permission is hereby granted, free of charge, to any person obtaining a
85.11 +// copy of this software and associated documentation files (the
85.12 +// "Software"), to deal in the Software without restriction, including
85.13 +// without limitation the rights to use, copy, modify, merge, publish,
85.14 +// distribute, sublicense, and/or sell copies of the Software, and to
85.15 +// permit persons to whom the Software is furnished to do so, subject to
85.16 +// the following conditions:
85.17 +//
85.18 +// The above copyright notice and this permission notice shall be included
85.19 +// in all copies or substantial portions of the Software.
85.20 +//
85.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
85.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
85.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
85.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
85.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
85.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
85.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
85.28 +// </copyright>
85.29 +// <summary>
85.30 +// Provides various algorithms for polygons and lines of ScreenPoint.
85.31 +// </summary>
85.32 +// --------------------------------------------------------------------------------------------------------------------
85.33 +namespace OxyPlot
85.34 +{
85.35 + using System.Collections.Generic;
85.36 +
85.37 + /// <summary>
85.38 + /// Provides algorithms for polygons and lines of <see cref="ScreenPoint"/>.
85.39 + /// </summary>
85.40 + public static class ScreenPointHelper
85.41 + {
85.42 + /// <summary>
85.43 + /// Finds the nearest point on the specified polyline.
85.44 + /// </summary>
85.45 + /// <param name="point">
85.46 + /// The point.
85.47 + /// </param>
85.48 + /// <param name="points">
85.49 + /// The points.
85.50 + /// </param>
85.51 + /// <returns>
85.52 + /// The nearest point.
85.53 + /// </returns>
85.54 + public static ScreenPoint FindNearestPointOnPolyline(ScreenPoint point, IList<ScreenPoint> points)
85.55 + {
85.56 + double minimumDistance = double.MaxValue;
85.57 + var nearestPoint = default(ScreenPoint);
85.58 +
85.59 + for (int i = 0; i + 1 < points.Count; i++)
85.60 + {
85.61 + var p1 = points[i];
85.62 + var p2 = points[i + 1];
85.63 + if (ScreenPoint.IsUndefined(p1) || ScreenPoint.IsUndefined(p2))
85.64 + {
85.65 + continue;
85.66 + }
85.67 +
85.68 + // Find the nearest point on the line segment.
85.69 + var nearestPointOnSegment = FindPointOnLine(point, p1, p2);
85.70 +
85.71 + if (ScreenPoint.IsUndefined(nearestPointOnSegment))
85.72 + {
85.73 + continue;
85.74 + }
85.75 +
85.76 + double l2 = (point - nearestPointOnSegment).LengthSquared;
85.77 +
85.78 + if (l2 < minimumDistance)
85.79 + {
85.80 + nearestPoint = nearestPointOnSegment;
85.81 + minimumDistance = l2;
85.82 + }
85.83 + }
85.84 +
85.85 + return nearestPoint;
85.86 + }
85.87 +
85.88 + /// <summary>
85.89 + /// Finds the point on line.
85.90 + /// </summary>
85.91 + /// <param name="p">
85.92 + /// The point.
85.93 + /// </param>
85.94 + /// <param name="p1">
85.95 + /// The first point on the line.
85.96 + /// </param>
85.97 + /// <param name="p2">
85.98 + /// The second point on the line.
85.99 + /// </param>
85.100 + /// <returns>
85.101 + /// The nearest point on the line.
85.102 + /// </returns>
85.103 + /// <remarks>
85.104 + /// See <a href="http://paulbourke.net/geometry/pointlineplane/">Bourke</a>.
85.105 + /// </remarks>
85.106 + public static ScreenPoint FindPointOnLine(ScreenPoint p, ScreenPoint p1, ScreenPoint p2)
85.107 + {
85.108 + double dx = p2.x - p1.x;
85.109 + double dy = p2.y - p1.y;
85.110 + double u = FindPositionOnLine(p, p1, p2);
85.111 +
85.112 + if (double.IsNaN(u))
85.113 + {
85.114 + u = 0;
85.115 + }
85.116 +
85.117 + if (u < 0)
85.118 + {
85.119 + u = 0;
85.120 + }
85.121 +
85.122 + if (u > 1)
85.123 + {
85.124 + u = 1;
85.125 + }
85.126 +
85.127 + return new ScreenPoint(p1.x + (u * dx), p1.y + (u * dy));
85.128 + }
85.129 +
85.130 + /// <summary>
85.131 + /// Finds the nearest point on line.
85.132 + /// </summary>
85.133 + /// <param name="p">
85.134 + /// The point.
85.135 + /// </param>
85.136 + /// <param name="p1">
85.137 + /// The start point on the line.
85.138 + /// </param>
85.139 + /// <param name="p2">
85.140 + /// The end point on the line.
85.141 + /// </param>
85.142 + /// <returns>
85.143 + /// The relative position of the nearest point.
85.144 + /// </returns>
85.145 + /// <remarks>
85.146 + /// See <a href="http://paulbourke.net/geometry/pointlineplane/">Bourke</a>.
85.147 + /// </remarks>
85.148 + public static double FindPositionOnLine(ScreenPoint p, ScreenPoint p1, ScreenPoint p2)
85.149 + {
85.150 + double dx = p2.x - p1.x;
85.151 + double dy = p2.y - p1.y;
85.152 + double u1 = ((p.x - p1.x) * dx) + ((p.y - p1.y) * dy);
85.153 + double u2 = (dx * dx) + (dy * dy);
85.154 +
85.155 + if (u2 < 1e-6)
85.156 + {
85.157 + return double.NaN;
85.158 + }
85.159 +
85.160 + return u1 / u2;
85.161 + }
85.162 +
85.163 + /// <summary>
85.164 + /// Determines whether the specified point is in the specified polygon.
85.165 + /// </summary>
85.166 + /// <param name="p">
85.167 + /// The point.
85.168 + /// </param>
85.169 + /// <param name="pts">
85.170 + /// The polygon points.
85.171 + /// </param>
85.172 + /// <returns>
85.173 + /// <c>true</c> if the point is in the polygon; otherwise, <c>false</c>.
85.174 + /// </returns>
85.175 + public static bool IsPointInPolygon(ScreenPoint p, IList<ScreenPoint> pts)
85.176 + {
85.177 + int nvert = pts.Count;
85.178 + bool c = false;
85.179 + for (int i = 0, j = nvert - 1; i < nvert; j = i++)
85.180 + {
85.181 + if (((pts[i].Y > p.Y) != (pts[j].Y > p.Y))
85.182 + && (p.X < ((pts[j].X - pts[i].X) * ((p.Y - pts[i].Y) / (pts[j].Y - pts[i].Y))) + pts[i].X))
85.183 + {
85.184 + c = !c;
85.185 + }
85.186 + }
85.187 +
85.188 + return c;
85.189 + }
85.190 +
85.191 + /// <summary>
85.192 + /// Resamples the points with the specified point distance limit.
85.193 + /// </summary>
85.194 + /// <param name="allPoints">
85.195 + /// All points.
85.196 + /// </param>
85.197 + /// <param name="minimumDistance">
85.198 + /// The minimum squared distance.
85.199 + /// </param>
85.200 + /// <returns>
85.201 + /// List of resampled points.
85.202 + /// </returns>
85.203 + public static IList<ScreenPoint> ResamplePoints(IList<ScreenPoint> allPoints, double minimumDistance)
85.204 + {
85.205 + double minimumSquaredDistance = minimumDistance * minimumDistance;
85.206 + int n = allPoints.Count;
85.207 + var result = new List<ScreenPoint>(n);
85.208 + if (n > 0)
85.209 + {
85.210 + result.Add(allPoints[0]);
85.211 + int i0 = 0;
85.212 + for (int i = 1; i < n; i++)
85.213 + {
85.214 + double distSquared = allPoints[i0].DistanceToSquared(allPoints[i]);
85.215 + if (distSquared < minimumSquaredDistance && i != n - 1)
85.216 + {
85.217 + continue;
85.218 + }
85.219 +
85.220 + i0 = i;
85.221 + result.Add(allPoints[i]);
85.222 + }
85.223 + }
85.224 +
85.225 + return result;
85.226 + }
85.227 +
85.228 + /// <summary>
85.229 + /// Gets the centroid of the specified polygon.
85.230 + /// </summary>
85.231 + /// <param name="points">
85.232 + /// The points.
85.233 + /// </param>
85.234 + /// <returns>
85.235 + /// The centroid.
85.236 + /// </returns>
85.237 + public static ScreenPoint GetCentroid(IList<ScreenPoint> points)
85.238 + {
85.239 + double cx = 0;
85.240 + double cy = 0;
85.241 + double a = 0;
85.242 +
85.243 + for (int i = 0; i < points.Count; i++)
85.244 + {
85.245 + int i1 = (i + 1) % points.Count;
85.246 + double da = (points[i].x * points[i1].y) - (points[i1].x * points[i].y);
85.247 + cx += (points[i].x + points[i1].x) * da;
85.248 + cy += (points[i].y + points[i1].y) * da;
85.249 + a += da;
85.250 + }
85.251 +
85.252 + a *= 0.5;
85.253 + cx /= 6 * a;
85.254 + cy /= 6 * a;
85.255 + return new ScreenPoint(cx, cy);
85.256 + }
85.257 + }
85.258 +}
85.259 \ No newline at end of file
86.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
86.2 +++ b/External/OxyPlot/OxyPlot/Foundation/ScreenVector.cs Sat Jun 08 16:53:22 2013 +0000
86.3 @@ -0,0 +1,155 @@
86.4 +// --------------------------------------------------------------------------------------------------------------------
86.5 +// <copyright file="ScreenVector.cs" company="OxyPlot">
86.6 +// The MIT License (MIT)
86.7 +//
86.8 +// Copyright (c) 2012 Oystein Bjorke
86.9 +//
86.10 +// Permission is hereby granted, free of charge, to any person obtaining a
86.11 +// copy of this software and associated documentation files (the
86.12 +// "Software"), to deal in the Software without restriction, including
86.13 +// without limitation the rights to use, copy, modify, merge, publish,
86.14 +// distribute, sublicense, and/or sell copies of the Software, and to
86.15 +// permit persons to whom the Software is furnished to do so, subject to
86.16 +// the following conditions:
86.17 +//
86.18 +// The above copyright notice and this permission notice shall be included
86.19 +// in all copies or substantial portions of the Software.
86.20 +//
86.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
86.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
86.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
86.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
86.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
86.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
86.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
86.28 +// </copyright>
86.29 +// <summary>
86.30 +// Represents a vector defined in the screen coordinate system.
86.31 +// </summary>
86.32 +// --------------------------------------------------------------------------------------------------------------------
86.33 +namespace OxyPlot
86.34 +{
86.35 + using System;
86.36 +
86.37 + /// <summary>
86.38 + /// Represents a vector defined in the screen coordinate system.
86.39 + /// </summary>
86.40 + public struct ScreenVector
86.41 + {
86.42 + /// <summary>
86.43 + /// The x-coordinate.
86.44 + /// </summary>
86.45 + internal double x;
86.46 +
86.47 + /// <summary>
86.48 + /// The y-coordinate.
86.49 + /// </summary>
86.50 + internal double y;
86.51 +
86.52 + /// <summary>
86.53 + /// Initializes a new instance of the <see cref="ScreenVector"/> structure.
86.54 + /// </summary>
86.55 + /// <param name="x">
86.56 + /// The x-coordinate.
86.57 + /// </param>
86.58 + /// <param name="y">
86.59 + /// The y-coordinate.
86.60 + /// </param>
86.61 + public ScreenVector(double x, double y)
86.62 + {
86.63 + this.x = x;
86.64 + this.y = y;
86.65 + }
86.66 +
86.67 + /// <summary>
86.68 + /// Gets the length.
86.69 + /// </summary>
86.70 + public double Length
86.71 + {
86.72 + get
86.73 + {
86.74 + return Math.Sqrt((this.x * this.x) + (this.y * this.y));
86.75 + }
86.76 + }
86.77 +
86.78 + /// <summary>
86.79 + /// Gets the length squared.
86.80 + /// </summary>
86.81 + public double LengthSquared
86.82 + {
86.83 + get
86.84 + {
86.85 + return (this.x * this.x) + (this.y * this.y);
86.86 + }
86.87 + }
86.88 +
86.89 + /// <summary>
86.90 + /// Gets or sets the x-coordinate.
86.91 + /// </summary>
86.92 + /// <value> The x-coordinate. </value>
86.93 + public double X
86.94 + {
86.95 + get
86.96 + {
86.97 + return this.x;
86.98 + }
86.99 +
86.100 + set
86.101 + {
86.102 + this.x = value;
86.103 + }
86.104 + }
86.105 +
86.106 + /// <summary>
86.107 + /// Gets or sets the y-coordinate.
86.108 + /// </summary>
86.109 + /// <value> The y-coordinate. </value>
86.110 + public double Y
86.111 + {
86.112 + get
86.113 + {
86.114 + return this.y;
86.115 + }
86.116 +
86.117 + set
86.118 + {
86.119 + this.y = value;
86.120 + }
86.121 + }
86.122 +
86.123 + /// <summary>
86.124 + /// Normalizes this vector.
86.125 + /// </summary>
86.126 + public void Normalize()
86.127 + {
86.128 + double l = Math.Sqrt((this.x * this.x) + (this.y * this.y));
86.129 + if (l > 0)
86.130 + {
86.131 + this.x /= l;
86.132 + this.y /= l;
86.133 + }
86.134 + }
86.135 +
86.136 + /// <summary>
86.137 + /// Returns a <see cref="System.String"/> that represents this instance.
86.138 + /// </summary>
86.139 + /// <returns>
86.140 + /// A <see cref="System.String"/> that represents this instance.
86.141 + /// </returns>
86.142 + public override string ToString()
86.143 + {
86.144 + return this.x + " " + this.y;
86.145 + }
86.146 +
86.147 + /// <summary>
86.148 + /// Implements the operator *.
86.149 + /// </summary>
86.150 + /// <param name="v"> The vector. </param>
86.151 + /// <param name="d"> The multiplication factor. </param>
86.152 + /// <returns> The result of the operator. </returns>
86.153 + public static ScreenVector operator *(ScreenVector v, double d)
86.154 + {
86.155 + return new ScreenVector(v.x * d, v.y * d);
86.156 + }
86.157 + }
86.158 +}
86.159 \ No newline at end of file
87.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
87.2 +++ b/External/OxyPlot/OxyPlot/Foundation/Size.cs Sat Jun 08 16:53:22 2013 +0000
87.3 @@ -0,0 +1,43 @@
87.4 +// --------------------------------------------------------------------------------------------------------------------
87.5 +// <copyright file="Size.cs" company="OxyPlot">
87.6 +// The MIT License (MIT)
87.7 +//
87.8 +// Copyright (c) 2012 Oystein Bjorke
87.9 +//
87.10 +// Permission is hereby granted, free of charge, to any person obtaining a
87.11 +// copy of this software and associated documentation files (the
87.12 +// "Software"), to deal in the Software without restriction, including
87.13 +// without limitation the rights to use, copy, modify, merge, publish,
87.14 +// distribute, sublicense, and/or sell copies of the Software, and to
87.15 +// permit persons to whom the Software is furnished to do so, subject to
87.16 +// the following conditions:
87.17 +//
87.18 +// The above copyright notice and this permission notice shall be included
87.19 +// in all copies or substantial portions of the Software.
87.20 +//
87.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
87.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
87.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
87.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
87.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
87.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
87.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
87.28 +// </copyright>
87.29 +// --------------------------------------------------------------------------------------------------------------------
87.30 +namespace OxyPlot
87.31 +{
87.32 + public struct Size
87.33 + {
87.34 + public double Width { get; set; }
87.35 + public double Height { get; set; }
87.36 +
87.37 + public static Size Empty = new Size(0,0);
87.38 +
87.39 + public Size(double width, double height)
87.40 + : this()
87.41 + {
87.42 + this.Width = width;
87.43 + this.Height = height;
87.44 + }
87.45 + }
87.46 +}
87.47 \ No newline at end of file
88.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
88.2 +++ b/External/OxyPlot/OxyPlot/Foundation/StreamExtensions.cs Sat Jun 08 16:53:22 2013 +0000
88.3 @@ -0,0 +1,25 @@
88.4 +namespace OxyPlot
88.5 +{
88.6 + using System.IO;
88.7 +
88.8 + /// <summary>
88.9 + /// Implements <see cref="Stream"/> extension methods.
88.10 + /// </summary>
88.11 + public static class StreamExtensions
88.12 + {
88.13 + /// <summary>
88.14 + /// Copies to the specified stream.
88.15 + /// </summary>
88.16 + /// <param name="input">The input stream.</param>
88.17 + /// <param name="output">The output stream.</param>
88.18 + public static void CopyTo(this Stream input, Stream output)
88.19 + {
88.20 + var buffer = new byte[32768];
88.21 + int read;
88.22 + while ((read = input.Read(buffer, 0, buffer.Length)) > 0)
88.23 + {
88.24 + output.Write(buffer, 0, read);
88.25 + }
88.26 + }
88.27 + }
88.28 +}
88.29 \ No newline at end of file
89.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
89.2 +++ b/External/OxyPlot/OxyPlot/Foundation/StringHelper.cs Sat Jun 08 16:53:22 2013 +0000
89.3 @@ -0,0 +1,169 @@
89.4 +// --------------------------------------------------------------------------------------------------------------------
89.5 +// <copyright file="StringHelper.cs" company="OxyPlot">
89.6 +// The MIT License (MIT)
89.7 +//
89.8 +// Copyright (c) 2012 Oystein Bjorke
89.9 +//
89.10 +// Permission is hereby granted, free of charge, to any person obtaining a
89.11 +// copy of this software and associated documentation files (the
89.12 +// "Software"), to deal in the Software without restriction, including
89.13 +// without limitation the rights to use, copy, modify, merge, publish,
89.14 +// distribute, sublicense, and/or sell copies of the Software, and to
89.15 +// permit persons to whom the Software is furnished to do so, subject to
89.16 +// the following conditions:
89.17 +//
89.18 +// The above copyright notice and this permission notice shall be included
89.19 +// in all copies or substantial portions of the Software.
89.20 +//
89.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
89.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
89.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
89.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
89.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
89.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
89.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
89.28 +// </copyright>
89.29 +// <summary>
89.30 +// Provides support for string formatting.
89.31 +// </summary>
89.32 +// --------------------------------------------------------------------------------------------------------------------
89.33 +namespace OxyPlot
89.34 +{
89.35 + using System;
89.36 + using System.Collections;
89.37 + using System.Text;
89.38 + using System.Text.RegularExpressions;
89.39 +
89.40 + /// <summary>
89.41 + /// Provides extended string formatting functionality.
89.42 + /// </summary>
89.43 + public static class StringHelper
89.44 + {
89.45 + /// <summary>
89.46 + /// The formatting expression.
89.47 + /// </summary>
89.48 + private static readonly Regex FormattingExpression = new Regex("{(?<Property>.+?)(?<Format>\\:.*?)?}");
89.49 +
89.50 + /// <summary>
89.51 + /// Replaces the format items in the specified string.
89.52 + /// </summary>
89.53 + /// <param name="provider">
89.54 + /// The culture specific format provider.
89.55 + /// </param>
89.56 + /// <param name="formatString">
89.57 + /// The format string.
89.58 + /// </param>
89.59 + /// <param name="item">
89.60 + /// The item.
89.61 + /// </param>
89.62 + /// <param name="values">
89.63 + /// The values.
89.64 + /// </param>
89.65 + /// <remarks>
89.66 + /// The formatString and values works as in string.Format. In addition, you can format properties of the item object by using the syntax {PropertyName:Formatstring}. E.g. if you have a "Value" property in your item's class, use "{Value:0.00}" to output the value with two digits. Note that this formatting is using reflection and does not have the same performance as string.Format.
89.67 + /// </remarks>
89.68 + /// <returns>
89.69 + /// The formatted string.
89.70 + /// </returns>
89.71 + public static string Format(IFormatProvider provider, string formatString, object item, params object[] values)
89.72 + {
89.73 + // Replace items on the format {Property[:Formatstring]}
89.74 + var s = FormattingExpression.Replace(
89.75 + formatString,
89.76 + delegate(Match match)
89.77 + {
89.78 + var property = match.Groups["Property"].Value;
89.79 + if (property.Length > 0 && char.IsDigit(property[0]))
89.80 + {
89.81 + return match.Value;
89.82 + }
89.83 +
89.84 + var pi = item.GetType().GetProperty(property);
89.85 + if (pi == null)
89.86 + {
89.87 + return string.Empty;
89.88 + }
89.89 +
89.90 + var v = pi.GetValue(item, null);
89.91 + var format = match.Groups["Format"].Value;
89.92 +
89.93 + var fs = "{0" + format + "}";
89.94 + return string.Format(provider, fs, v);
89.95 + });
89.96 +
89.97 + // Also apply the standard formatting
89.98 + s = string.Format(provider, s, values);
89.99 + return s;
89.100 + }
89.101 +
89.102 + /// <summary>
89.103 + /// Creates a valid file name.
89.104 + /// </summary>
89.105 + /// <param name="title">
89.106 + /// The title.
89.107 + /// </param>
89.108 + /// <param name="extension">
89.109 + /// The extension.
89.110 + /// </param>
89.111 + /// <returns>
89.112 + /// A file name.
89.113 + /// </returns>
89.114 + public static string CreateValidFileName(string title, string extension)
89.115 + {
89.116 + string validFileName = title.Trim();
89.117 + var invalidFileNameChars = "/?<>\\:*|\0\t\r\n".ToCharArray();
89.118 + foreach (char invalChar in invalidFileNameChars)
89.119 + {
89.120 + validFileName = validFileName.Replace(invalChar.ToString(), string.Empty);
89.121 + }
89.122 +
89.123 + foreach (char invalChar in invalidFileNameChars)
89.124 + {
89.125 + validFileName = validFileName.Replace(invalChar.ToString(), string.Empty);
89.126 + }
89.127 +
89.128 + if (validFileName.Length > 160)
89.129 + {
89.130 + // safe value threshold is 260
89.131 + validFileName = validFileName.Remove(156) + "...";
89.132 + }
89.133 +
89.134 + return validFileName + extension;
89.135 + }
89.136 +
89.137 + /// <summary>
89.138 + /// Creates a string from a collection of items.
89.139 + /// </summary>
89.140 + /// <param name="provider">
89.141 + /// The provider.
89.142 + /// </param>
89.143 + /// <param name="items">
89.144 + /// The items.
89.145 + /// </param>
89.146 + /// <param name="formatstring">
89.147 + /// The format string to apply to each item.
89.148 + /// </param>
89.149 + /// <param name="separator">
89.150 + /// The separator.
89.151 + /// </param>
89.152 + /// <returns>
89.153 + /// The collection as a string.
89.154 + /// </returns>
89.155 + public static object CreateList(
89.156 + IFormatProvider provider, IEnumerable items, string formatstring, string separator = ", ")
89.157 + {
89.158 + var sb = new StringBuilder();
89.159 + foreach (var item in items)
89.160 + {
89.161 + if (sb.Length > 0)
89.162 + {
89.163 + sb.Append(separator);
89.164 + }
89.165 +
89.166 + sb.Append(string.Format(provider, formatstring, item));
89.167 + }
89.168 +
89.169 + return sb.ToString();
89.170 + }
89.171 + }
89.172 +}
89.173 \ No newline at end of file
90.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
90.2 +++ b/External/OxyPlot/OxyPlot/Foundation/SutherlandHodgmanClipping.cs Sat Jun 08 16:53:22 2013 +0000
90.3 @@ -0,0 +1,233 @@
90.4 +// --------------------------------------------------------------------------------------------------------------------
90.5 +// <copyright file="SutherlandHodgmanClipping.cs" company="OxyPlot">
90.6 +// The MIT License (MIT)
90.7 +//
90.8 +// Copyright (c) 2012 Oystein Bjorke
90.9 +//
90.10 +// Permission is hereby granted, free of charge, to any person obtaining a
90.11 +// copy of this software and associated documentation files (the
90.12 +// "Software"), to deal in the Software without restriction, including
90.13 +// without limitation the rights to use, copy, modify, merge, publish,
90.14 +// distribute, sublicense, and/or sell copies of the Software, and to
90.15 +// permit persons to whom the Software is furnished to do so, subject to
90.16 +// the following conditions:
90.17 +//
90.18 +// The above copyright notice and this permission notice shall be included
90.19 +// in all copies or substantial portions of the Software.
90.20 +//
90.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
90.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
90.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
90.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
90.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
90.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
90.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
90.28 +// </copyright>
90.29 +// <summary>
90.30 +// Polygon clipping by the sutherland-hodgman algortihm.
90.31 +// </summary>
90.32 +// --------------------------------------------------------------------------------------------------------------------
90.33 +namespace OxyPlot
90.34 +{
90.35 + using System;
90.36 + using System.Collections.Generic;
90.37 +
90.38 + /// <summary>
90.39 + /// Provides polygon clipping by the Sutherland-Hodgman algortihm.
90.40 + /// </summary>
90.41 + public static class SutherlandHodgmanClipping
90.42 + {
90.43 + /// <summary>
90.44 + /// The rectangle edge.
90.45 + /// </summary>
90.46 + private enum RectangleEdge
90.47 + {
90.48 + /// <summary>
90.49 + /// The left.
90.50 + /// </summary>
90.51 + Left,
90.52 +
90.53 + /// <summary>
90.54 + /// The right.
90.55 + /// </summary>
90.56 + Right,
90.57 +
90.58 + /// <summary>
90.59 + /// The top.
90.60 + /// </summary>
90.61 + Top,
90.62 +
90.63 + /// <summary>
90.64 + /// The bottom.
90.65 + /// </summary>
90.66 + Bottom
90.67 + }
90.68 +
90.69 + /// <summary>
90.70 + /// The Sutherland-Hodgman polygon clipping algorithm.
90.71 + /// </summary>
90.72 + /// <remarks>
90.73 + /// See http://ezekiel.vancouver.wsu.edu/~cs442/lectures/clip/clip/index.html
90.74 + /// </remarks>
90.75 + /// <param name="bounds">
90.76 + /// The bounds.
90.77 + /// </param>
90.78 + /// <param name="v">
90.79 + /// The polygon points.
90.80 + /// </param>
90.81 + /// <returns>
90.82 + /// The clipped points.
90.83 + /// </returns>
90.84 + public static List<ScreenPoint> ClipPolygon(OxyRect bounds, IList<ScreenPoint> v)
90.85 + {
90.86 + List<ScreenPoint> p1 = ClipOneAxis(bounds, RectangleEdge.Left, v);
90.87 + List<ScreenPoint> p2 = ClipOneAxis(bounds, RectangleEdge.Right, p1);
90.88 + List<ScreenPoint> p3 = ClipOneAxis(bounds, RectangleEdge.Top, p2);
90.89 + return ClipOneAxis(bounds, RectangleEdge.Bottom, p3);
90.90 + }
90.91 +
90.92 + /// <summary>
90.93 + /// Clips to one axis.
90.94 + /// </summary>
90.95 + /// <param name="bounds">
90.96 + /// The bounds.
90.97 + /// </param>
90.98 + /// <param name="edge">
90.99 + /// The edge.
90.100 + /// </param>
90.101 + /// <param name="v">
90.102 + /// The points of the polygon.
90.103 + /// </param>
90.104 + /// <returns>
90.105 + /// The clipped points.
90.106 + /// </returns>
90.107 + private static List<ScreenPoint> ClipOneAxis(OxyRect bounds, RectangleEdge edge, IList<ScreenPoint> v)
90.108 + {
90.109 + if (v.Count == 0)
90.110 + {
90.111 + return new List<ScreenPoint>();
90.112 + }
90.113 +
90.114 + var polygon = new List<ScreenPoint>(v.Count);
90.115 +
90.116 + var s = v[v.Count - 1];
90.117 +
90.118 + for (int i = 0; i < v.Count; ++i)
90.119 + {
90.120 + var p = v[i];
90.121 + bool pin = IsInside(bounds, edge, p);
90.122 + bool sin = IsInside(bounds, edge, s);
90.123 +
90.124 + if (sin && pin)
90.125 + {
90.126 + // case 1: inside -> inside
90.127 + polygon.Add(p);
90.128 + }
90.129 + else if (sin)
90.130 + {
90.131 + // case 2: inside -> outside
90.132 + polygon.Add(LineIntercept(bounds, edge, s, p));
90.133 + }
90.134 + else if (!pin)
90.135 + {
90.136 + // case 3: outside -> outside
90.137 + // emit nothing
90.138 + }
90.139 + else
90.140 + {
90.141 + // case 4: outside -> inside
90.142 + polygon.Add(LineIntercept(bounds, edge, s, p));
90.143 + polygon.Add(p);
90.144 + }
90.145 +
90.146 + s = p;
90.147 + }
90.148 +
90.149 + return polygon;
90.150 + }
90.151 +
90.152 + /// <summary>
90.153 + /// Determines whether the specified point is inside the edge/bounds.
90.154 + /// </summary>
90.155 + /// <param name="bounds">The bounds.</param>
90.156 + /// <param name="edge">The edge to test.</param>
90.157 + /// <param name="p">The point.</param>
90.158 + /// <returns>
90.159 + /// <c>true</c> if the specified point is inside; otherwise, <c>false</c>.
90.160 + /// </returns>
90.161 + private static bool IsInside(OxyRect bounds, RectangleEdge edge, ScreenPoint p)
90.162 + {
90.163 + switch (edge)
90.164 + {
90.165 + case RectangleEdge.Left:
90.166 + return !(p.X < bounds.Left);
90.167 +
90.168 + case RectangleEdge.Right:
90.169 + return !(p.X >= bounds.Right);
90.170 +
90.171 + case RectangleEdge.Top:
90.172 + return !(p.Y < bounds.Top);
90.173 +
90.174 + case RectangleEdge.Bottom:
90.175 + return !(p.Y >= bounds.Bottom);
90.176 +
90.177 + default:
90.178 + throw new ArgumentException("edge");
90.179 + }
90.180 + }
90.181 +
90.182 + /// <summary>
90.183 + /// Fines the edge interception.
90.184 + /// </summary>
90.185 + /// <param name="bounds">The bounds.</param>
90.186 + /// <param name="edge">The edge.</param>
90.187 + /// <param name="a">The first point.</param>
90.188 + /// <param name="b">The second point.</param>
90.189 + /// <returns>The interception.</returns>
90.190 + private static ScreenPoint LineIntercept(OxyRect bounds, RectangleEdge edge, ScreenPoint a, ScreenPoint b)
90.191 + {
90.192 + if (a.x == b.x && a.y == b.y)
90.193 + {
90.194 + return a;
90.195 + }
90.196 +
90.197 + switch (edge)
90.198 + {
90.199 + case RectangleEdge.Bottom:
90.200 + if (b.Y == a.Y)
90.201 + {
90.202 + throw new ArgumentException("no intercept found");
90.203 + }
90.204 +
90.205 + return new ScreenPoint(a.X + (((b.X - a.X) * (bounds.Bottom - a.Y)) / (b.Y - a.Y)), bounds.Bottom);
90.206 +
90.207 + case RectangleEdge.Left:
90.208 + if (b.X == a.X)
90.209 + {
90.210 + throw new ArgumentException("no intercept found");
90.211 + }
90.212 +
90.213 + return new ScreenPoint(bounds.Left, a.Y + (((b.Y - a.Y) * (bounds.Left - a.X)) / (b.X - a.X)));
90.214 +
90.215 + case RectangleEdge.Right:
90.216 + if (b.X == a.X)
90.217 + {
90.218 + throw new ArgumentException("no intercept found");
90.219 + }
90.220 +
90.221 + return new ScreenPoint(bounds.Right, a.Y + (((b.Y - a.Y) * (bounds.Right - a.X)) / (b.X - a.X)));
90.222 +
90.223 + case RectangleEdge.Top:
90.224 + if (b.Y == a.Y)
90.225 + {
90.226 + throw new ArgumentException("no intercept found");
90.227 + }
90.228 +
90.229 + return new ScreenPoint(a.X + (((b.X - a.X) * (bounds.Top - a.Y)) / (b.Y - a.Y)), bounds.Top);
90.230 + }
90.231 +
90.232 + throw new ArgumentException("no intercept found");
90.233 + }
90.234 +
90.235 + }
90.236 +}
90.237 \ No newline at end of file
91.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
91.2 +++ b/External/OxyPlot/OxyPlot/Foundation/VerticalAlignment.cs Sat Jun 08 16:53:22 2013 +0000
91.3 @@ -0,0 +1,52 @@
91.4 +// --------------------------------------------------------------------------------------------------------------------
91.5 +// <copyright file="VerticalAlignment.cs" company="OxyPlot">
91.6 +// The MIT License (MIT)
91.7 +//
91.8 +// Copyright (c) 2012 Oystein Bjorke
91.9 +//
91.10 +// Permission is hereby granted, free of charge, to any person obtaining a
91.11 +// copy of this software and associated documentation files (the
91.12 +// "Software"), to deal in the Software without restriction, including
91.13 +// without limitation the rights to use, copy, modify, merge, publish,
91.14 +// distribute, sublicense, and/or sell copies of the Software, and to
91.15 +// permit persons to whom the Software is furnished to do so, subject to
91.16 +// the following conditions:
91.17 +//
91.18 +// The above copyright notice and this permission notice shall be included
91.19 +// in all copies or substantial portions of the Software.
91.20 +//
91.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
91.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
91.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
91.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
91.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
91.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
91.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
91.28 +// </copyright>
91.29 +// <summary>
91.30 +// Vertical text alignment.
91.31 +// </summary>
91.32 +// --------------------------------------------------------------------------------------------------------------------
91.33 +namespace OxyPlot
91.34 +{
91.35 + /// <summary>
91.36 + /// Specifies the vertical alignment.
91.37 + /// </summary>
91.38 + public enum VerticalAlignment
91.39 + {
91.40 + /// <summary>
91.41 + /// Aligned at the top.
91.42 + /// </summary>
91.43 + Top = -1,
91.44 +
91.45 + /// <summary>
91.46 + /// Aligned in the middle.
91.47 + /// </summary>
91.48 + Middle = 0,
91.49 +
91.50 + /// <summary>
91.51 + /// Aligned at the bottom.
91.52 + /// </summary>
91.53 + Bottom = 1
91.54 + }
91.55 +}
91.56 \ No newline at end of file
92.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
92.2 +++ b/External/OxyPlot/OxyPlot/Foundation/XmlWriterBase.cs Sat Jun 08 16:53:22 2013 +0000
92.3 @@ -0,0 +1,233 @@
92.4 +// --------------------------------------------------------------------------------------------------------------------
92.5 +// <copyright file="XmlWriterBase.cs" company="OxyPlot">
92.6 +// The MIT License (MIT)
92.7 +//
92.8 +// Copyright (c) 2012 Oystein Bjorke
92.9 +//
92.10 +// Permission is hereby granted, free of charge, to any person obtaining a
92.11 +// copy of this software and associated documentation files (the
92.12 +// "Software"), to deal in the Software without restriction, including
92.13 +// without limitation the rights to use, copy, modify, merge, publish,
92.14 +// distribute, sublicense, and/or sell copies of the Software, and to
92.15 +// permit persons to whom the Software is furnished to do so, subject to
92.16 +// the following conditions:
92.17 +//
92.18 +// The above copyright notice and this permission notice shall be included
92.19 +// in all copies or substantial portions of the Software.
92.20 +//
92.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
92.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
92.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
92.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
92.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
92.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
92.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
92.28 +// </copyright>
92.29 +// <summary>
92.30 +// Abstract base class for exporters that write xml.
92.31 +// </summary>
92.32 +// --------------------------------------------------------------------------------------------------------------------
92.33 +namespace OxyPlot
92.34 +{
92.35 + using System;
92.36 + using System.IO;
92.37 + using System.Text;
92.38 + using System.Xml;
92.39 +
92.40 + /// <summary>
92.41 + /// Provides an abstract base class for exporters that write xml.
92.42 + /// </summary>
92.43 + public abstract class XmlWriterBase : IDisposable
92.44 + {
92.45 + /// <summary>
92.46 + /// The xml writer.
92.47 + /// </summary>
92.48 + private XmlWriter w;
92.49 +
92.50 + /// <summary>
92.51 + /// The disposed flag.
92.52 + /// </summary>
92.53 + private bool disposed;
92.54 +
92.55 + /// <summary>
92.56 + /// Initializes a new instance of the <see cref = "XmlWriterBase" /> class.
92.57 + /// </summary>
92.58 + protected XmlWriterBase()
92.59 + {
92.60 + }
92.61 +
92.62 + /// <summary>
92.63 + /// Initializes a new instance of the <see cref="XmlWriterBase"/> class.
92.64 + /// </summary>
92.65 + /// <param name="stream">
92.66 + /// The stream.
92.67 + /// </param>
92.68 + protected XmlWriterBase(Stream stream)
92.69 + {
92.70 + this.w = XmlWriter.Create(stream, new XmlWriterSettings { Indent = true, Encoding = Encoding.UTF8 });
92.71 + }
92.72 +
92.73 + /// <summary>
92.74 + /// Closes this instance.
92.75 + /// </summary>
92.76 + public virtual void Close()
92.77 + {
92.78 + }
92.79 +
92.80 + /// <summary>
92.81 + /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
92.82 + /// </summary>
92.83 + public void Dispose()
92.84 + {
92.85 + this.Dispose(true);
92.86 + GC.SuppressFinalize(this);
92.87 + }
92.88 +
92.89 + /// <summary>
92.90 + /// Flushes this instance.
92.91 + /// </summary>
92.92 + public void Flush()
92.93 + {
92.94 + this.w.Flush();
92.95 + }
92.96 +
92.97 + /// <summary>
92.98 + /// The write attribute string.
92.99 + /// </summary>
92.100 + /// <param name="name">
92.101 + /// The name.
92.102 + /// </param>
92.103 + /// <param name="value">
92.104 + /// The value.
92.105 + /// </param>
92.106 + protected void WriteAttributeString(string name, string value)
92.107 + {
92.108 + this.w.WriteAttributeString(name, value);
92.109 + }
92.110 +
92.111 + /// <summary>
92.112 + /// The write doc type.
92.113 + /// </summary>
92.114 + /// <param name="name">
92.115 + /// The name.
92.116 + /// </param>
92.117 + /// <param name="pubid">
92.118 + /// The pubid.
92.119 + /// </param>
92.120 + /// <param name="sysid">
92.121 + /// The sysid.
92.122 + /// </param>
92.123 + /// <param name="subset">
92.124 + /// The subset.
92.125 + /// </param>
92.126 + protected void WriteDocType(string name, string pubid, string sysid, string subset)
92.127 + {
92.128 + this.w.WriteDocType(name, pubid, sysid, subset);
92.129 + }
92.130 +
92.131 + /// <summary>
92.132 + /// The write element string.
92.133 + /// </summary>
92.134 + /// <param name="name">
92.135 + /// The name.
92.136 + /// </param>
92.137 + /// <param name="text">
92.138 + /// The text.
92.139 + /// </param>
92.140 + protected void WriteElementString(string name, string text)
92.141 + {
92.142 + this.w.WriteElementString(name, text);
92.143 + }
92.144 +
92.145 + /// <summary>
92.146 + /// The write end document.
92.147 + /// </summary>
92.148 + protected void WriteEndDocument()
92.149 + {
92.150 + this.w.WriteEndDocument();
92.151 + }
92.152 +
92.153 + /// <summary>
92.154 + /// The write end element.
92.155 + /// </summary>
92.156 + protected void WriteEndElement()
92.157 + {
92.158 + this.w.WriteEndElement();
92.159 + }
92.160 +
92.161 + /// <summary>
92.162 + /// The write raw.
92.163 + /// </summary>
92.164 + /// <param name="text">
92.165 + /// The text.
92.166 + /// </param>
92.167 + protected void WriteRaw(string text)
92.168 + {
92.169 + this.w.WriteRaw(text);
92.170 + }
92.171 +
92.172 + /// <summary>
92.173 + /// The write start document.
92.174 + /// </summary>
92.175 + /// <param name="standalone">
92.176 + /// The standalone.
92.177 + /// </param>
92.178 + protected void WriteStartDocument(bool standalone)
92.179 + {
92.180 + this.w.WriteStartDocument(standalone);
92.181 + }
92.182 +
92.183 + /// <summary>
92.184 + /// The write start element.
92.185 + /// </summary>
92.186 + /// <param name="name">
92.187 + /// The name.
92.188 + /// </param>
92.189 + protected void WriteStartElement(string name)
92.190 + {
92.191 + this.w.WriteStartElement(name);
92.192 + }
92.193 +
92.194 + /// <summary>
92.195 + /// The write start element.
92.196 + /// </summary>
92.197 + /// <param name="name">
92.198 + /// The name.
92.199 + /// </param>
92.200 + /// <param name="ns">
92.201 + /// The ns.
92.202 + /// </param>
92.203 + protected void WriteStartElement(string name, string ns)
92.204 + {
92.205 + this.w.WriteStartElement(name, ns);
92.206 + }
92.207 +
92.208 + /// <summary>
92.209 + /// The write string.
92.210 + /// </summary>
92.211 + /// <param name="text">
92.212 + /// The text.
92.213 + /// </param>
92.214 + protected void WriteString(string text)
92.215 + {
92.216 + this.w.WriteString(text);
92.217 + }
92.218 +
92.219 + /// <summary>
92.220 + /// Releases unmanaged and - optionally - managed resources
92.221 + /// </summary>
92.222 + /// <param name="disposing"><c>true</c> to release both managed and unmanaged resources; <c>false</c> to release only unmanaged resources.</param>
92.223 + private void Dispose(bool disposing)
92.224 + {
92.225 + if (!this.disposed)
92.226 + {
92.227 + if (disposing)
92.228 + {
92.229 + this.Close();
92.230 + }
92.231 + }
92.232 +
92.233 + this.disposed = true;
92.234 + }
92.235 + }
92.236 +}
92.237 \ No newline at end of file
93.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
93.2 +++ b/External/OxyPlot/OxyPlot/LibraryDoc.cs Sat Jun 08 16:53:22 2013 +0000
93.3 @@ -0,0 +1,37 @@
93.4 +// --------------------------------------------------------------------------------------------------------------------
93.5 +// <copyright file="LibraryDoc.cs" company="OxyPlot">
93.6 +// The MIT License (MIT)
93.7 +//
93.8 +// Copyright (c) 2012 Oystein Bjorke
93.9 +//
93.10 +// Permission is hereby granted, free of charge, to any person obtaining a
93.11 +// copy of this software and associated documentation files (the
93.12 +// "Software"), to deal in the Software without restriction, including
93.13 +// without limitation the rights to use, copy, modify, merge, publish,
93.14 +// distribute, sublicense, and/or sell copies of the Software, and to
93.15 +// permit persons to whom the Software is furnished to do so, subject to
93.16 +// the following conditions:
93.17 +//
93.18 +// The above copyright notice and this permission notice shall be included
93.19 +// in all copies or substantial portions of the Software.
93.20 +//
93.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
93.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
93.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
93.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
93.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
93.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
93.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
93.28 +// </copyright>
93.29 +// --------------------------------------------------------------------------------------------------------------------
93.30 +
93.31 +namespace OxyPlot
93.32 +{
93.33 + /// <summary>
93.34 + /// The OxyPlot solution provides plotting functionality on many platforms.
93.35 + /// </summary>
93.36 + [System.Runtime.CompilerServices.CompilerGenerated]
93.37 + internal class LibraryDoc
93.38 + {
93.39 + }
93.40 +}
93.41 \ No newline at end of file
94.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
94.2 +++ b/External/OxyPlot/OxyPlot/Manipulators/CursorType.cs Sat Jun 08 16:53:22 2013 +0000
94.3 @@ -0,0 +1,62 @@
94.4 +// --------------------------------------------------------------------------------------------------------------------
94.5 +// <copyright file="CursorType.cs" company="OxyPlot">
94.6 +// The MIT License (MIT)
94.7 +//
94.8 +// Copyright (c) 2012 Oystein Bjorke
94.9 +//
94.10 +// Permission is hereby granted, free of charge, to any person obtaining a
94.11 +// copy of this software and associated documentation files (the
94.12 +// "Software"), to deal in the Software without restriction, including
94.13 +// without limitation the rights to use, copy, modify, merge, publish,
94.14 +// distribute, sublicense, and/or sell copies of the Software, and to
94.15 +// permit persons to whom the Software is furnished to do so, subject to
94.16 +// the following conditions:
94.17 +//
94.18 +// The above copyright notice and this permission notice shall be included
94.19 +// in all copies or substantial portions of the Software.
94.20 +//
94.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
94.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
94.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
94.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
94.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
94.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
94.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
94.28 +// </copyright>
94.29 +// <summary>
94.30 +// Specifies the cursor type.
94.31 +// </summary>
94.32 +// --------------------------------------------------------------------------------------------------------------------
94.33 +namespace OxyPlot
94.34 +{
94.35 + /// <summary>
94.36 + /// Specifies the cursor type.
94.37 + /// </summary>
94.38 + public enum CursorType
94.39 + {
94.40 + /// <summary>
94.41 + /// The default cursor
94.42 + /// </summary>
94.43 + Default = 0,
94.44 +
94.45 + /// <summary>
94.46 + /// The pan cursor
94.47 + /// </summary>
94.48 + Pan,
94.49 +
94.50 + /// <summary>
94.51 + /// The zoom rectangle cursor
94.52 + /// </summary>
94.53 + ZoomRectangle,
94.54 +
94.55 + /// <summary>
94.56 + /// The horizontal zoom cursor
94.57 + /// </summary>
94.58 + ZoomHorizontal,
94.59 +
94.60 + /// <summary>
94.61 + /// The vertical zoom cursor
94.62 + /// </summary>
94.63 + ZoomVertical
94.64 + }
94.65 +}
94.66 \ No newline at end of file
95.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
95.2 +++ b/External/OxyPlot/OxyPlot/Manipulators/IPlotControl.cs Sat Jun 08 16:53:22 2013 +0000
95.3 @@ -0,0 +1,176 @@
95.4 +// --------------------------------------------------------------------------------------------------------------------
95.5 +// <copyright file="IPlotControl.cs" company="OxyPlot">
95.6 +// The MIT License (MIT)
95.7 +//
95.8 +// Copyright (c) 2012 Oystein Bjorke
95.9 +//
95.10 +// Permission is hereby granted, free of charge, to any person obtaining a
95.11 +// copy of this software and associated documentation files (the
95.12 +// "Software"), to deal in the Software without restriction, including
95.13 +// without limitation the rights to use, copy, modify, merge, publish,
95.14 +// distribute, sublicense, and/or sell copies of the Software, and to
95.15 +// permit persons to whom the Software is furnished to do so, subject to
95.16 +// the following conditions:
95.17 +//
95.18 +// The above copyright notice and this permission notice shall be included
95.19 +// in all copies or substantial portions of the Software.
95.20 +//
95.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
95.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
95.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
95.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
95.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
95.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
95.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
95.28 +// </copyright>
95.29 +// <summary>
95.30 +// Interface for Plot controls.
95.31 +// </summary>
95.32 +// --------------------------------------------------------------------------------------------------------------------
95.33 +namespace OxyPlot
95.34 +{
95.35 + using OxyPlot.Annotations;
95.36 + using OxyPlot.Axes;
95.37 + using OxyPlot.Series;
95.38 +
95.39 + /// <summary>
95.40 + /// Defines functionality in the Plot controls.
95.41 + /// </summary>
95.42 + public interface IPlotControl
95.43 + {
95.44 + /// <summary>
95.45 + /// Gets the actual model.
95.46 + /// </summary>
95.47 + /// <value>The actual model.</value>
95.48 + PlotModel ActualModel { get; }
95.49 +
95.50 + /// <summary>
95.51 + /// Gets the axes from a point.
95.52 + /// </summary>
95.53 + /// <param name="pt">
95.54 + /// The point.
95.55 + /// </param>
95.56 + /// <param name="xaxis">
95.57 + /// The x-axis.
95.58 + /// </param>
95.59 + /// <param name="yaxis">
95.60 + /// The y-axis.
95.61 + /// </param>
95.62 + void GetAxesFromPoint(ScreenPoint pt, out Axis xaxis, out Axis yaxis);
95.63 +
95.64 + /// <summary>
95.65 + /// Gets the series from point.
95.66 + /// </summary>
95.67 + /// <param name="pt">
95.68 + /// The point (screen coordinates).
95.69 + /// </param>
95.70 + /// <param name="limit">
95.71 + /// The maximum allowed distance.
95.72 + /// </param>
95.73 + /// <returns>
95.74 + /// The series.
95.75 + /// </returns>
95.76 + Series.Series GetSeriesFromPoint(ScreenPoint pt, double limit = 100);
95.77 +
95.78 + /// <summary>
95.79 + /// Hides the tracker.
95.80 + /// </summary>
95.81 + void HideTracker();
95.82 +
95.83 + /// <summary>
95.84 + /// Hides the zoom rectangle.
95.85 + /// </summary>
95.86 + void HideZoomRectangle();
95.87 +
95.88 + /// <summary>
95.89 + /// Invalidate the plot (not blocking the UI thread)
95.90 + /// </summary>
95.91 + /// <param name="updateData">
95.92 + /// if set to <c>true</c>, all data collections will be updated.
95.93 + /// </param>
95.94 + void InvalidatePlot(bool updateData = true);
95.95 +
95.96 + /// <summary>
95.97 + /// Pans the specified axis.
95.98 + /// </summary>
95.99 + /// <param name="axis">
95.100 + /// The axis.
95.101 + /// </param>
95.102 + /// <param name="ppt">
95.103 + /// The previous point (screen coordinates).
95.104 + /// </param>
95.105 + /// <param name="cpt">
95.106 + /// The current point (screen coordinates).
95.107 + /// </param>
95.108 + void Pan(Axis axis, ScreenPoint ppt, ScreenPoint cpt);
95.109 +
95.110 + /// <summary>
95.111 + /// Refresh the plot immediately (blocking UI thread)
95.112 + /// </summary>
95.113 + /// <param name="updateData">
95.114 + /// if set to <c>true</c>, all data collections will be updated.
95.115 + /// </param>
95.116 + void RefreshPlot(bool updateData = true);
95.117 +
95.118 + /// <summary>
95.119 + /// Resets the specified axis.
95.120 + /// </summary>
95.121 + /// <param name="axis">
95.122 + /// The axis.
95.123 + /// </param>
95.124 + void Reset(Axis axis);
95.125 +
95.126 + /// <summary>
95.127 + /// Sets the cursor type.
95.128 + /// </summary>
95.129 + /// <param name="cursorType">
95.130 + /// The cursor type.
95.131 + /// </param>
95.132 + void SetCursorType(CursorType cursorType);
95.133 +
95.134 + /// <summary>
95.135 + /// Shows the tracker.
95.136 + /// </summary>
95.137 + /// <param name="trackerHitResult">
95.138 + /// The tracker data.
95.139 + /// </param>
95.140 + void ShowTracker(TrackerHitResult trackerHitResult);
95.141 +
95.142 + /// <summary>
95.143 + /// Shows the zoom rectangle.
95.144 + /// </summary>
95.145 + /// <param name="r">
95.146 + /// The rectangle.
95.147 + /// </param>
95.148 + void ShowZoomRectangle(OxyRect r);
95.149 +
95.150 + /// <summary>
95.151 + /// Zooms the specified axis to the specified values.
95.152 + /// </summary>
95.153 + /// <param name="axis">
95.154 + /// The axis.
95.155 + /// </param>
95.156 + /// <param name="p1">
95.157 + /// The new minimum value.
95.158 + /// </param>
95.159 + /// <param name="p2">
95.160 + /// The new maximum value.
95.161 + /// </param>
95.162 + void Zoom(Axis axis, double p1, double p2);
95.163 +
95.164 + /// <summary>
95.165 + /// Zooms at the specified position.
95.166 + /// </summary>
95.167 + /// <param name="axis">
95.168 + /// The axis.
95.169 + /// </param>
95.170 + /// <param name="factor">
95.171 + /// The zoom factor.
95.172 + /// </param>
95.173 + /// <param name="x">
95.174 + /// The position to zoom at.
95.175 + /// </param>
95.176 + void ZoomAt(Axis axis, double factor, double x);
95.177 +
95.178 + }
95.179 +}
95.180 \ No newline at end of file
96.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
96.2 +++ b/External/OxyPlot/OxyPlot/Manipulators/ManipulationEventArgs.cs Sat Jun 08 16:53:22 2013 +0000
96.3 @@ -0,0 +1,67 @@
96.4 +// --------------------------------------------------------------------------------------------------------------------
96.5 +// <copyright file="ManipulationEventArgs.cs" company="OxyPlot">
96.6 +// The MIT License (MIT)
96.7 +//
96.8 +// Copyright (c) 2012 Oystein Bjorke
96.9 +//
96.10 +// Permission is hereby granted, free of charge, to any person obtaining a
96.11 +// copy of this software and associated documentation files (the
96.12 +// "Software"), to deal in the Software without restriction, including
96.13 +// without limitation the rights to use, copy, modify, merge, publish,
96.14 +// distribute, sublicense, and/or sell copies of the Software, and to
96.15 +// permit persons to whom the Software is furnished to do so, subject to
96.16 +// the following conditions:
96.17 +//
96.18 +// The above copyright notice and this permission notice shall be included
96.19 +// in all copies or substantial portions of the Software.
96.20 +//
96.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
96.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
96.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
96.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
96.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
96.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
96.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
96.28 +// </copyright>
96.29 +// <summary>
96.30 +// Provides data for the manipulation events.
96.31 +// </summary>
96.32 +// --------------------------------------------------------------------------------------------------------------------
96.33 +namespace OxyPlot
96.34 +{
96.35 + /// <summary>
96.36 + /// Provides data for the manipulation events.
96.37 + /// </summary>
96.38 + public class ManipulationEventArgs
96.39 + {
96.40 + /// <summary>
96.41 + /// Initializes a new instance of the <see cref="ManipulationEventArgs"/> class.
96.42 + /// </summary>
96.43 + /// <param name="currentPosition">
96.44 + /// The current position.
96.45 + /// </param>
96.46 + public ManipulationEventArgs(ScreenPoint currentPosition)
96.47 + {
96.48 + this.CurrentPosition = currentPosition;
96.49 + }
96.50 +
96.51 + /// <summary>
96.52 + /// Gets the current position.
96.53 + /// </summary>
96.54 + /// <value>The current position.</value>
96.55 + public ScreenPoint CurrentPosition { get; private set; }
96.56 +
96.57 + /// <summary>
96.58 + /// Gets or sets the X scaling factor.
96.59 + /// </summary>
96.60 + /// <value>The scale value.</value>
96.61 + public double ScaleX { get; set; }
96.62 +
96.63 + /// <summary>
96.64 + /// Gets or sets the Y scaling factor.
96.65 + /// </summary>
96.66 + /// <value>The scale value.</value>
96.67 + public double ScaleY { get; set; }
96.68 +
96.69 + }
96.70 +}
96.71 \ No newline at end of file
97.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
97.2 +++ b/External/OxyPlot/OxyPlot/Manipulators/ManipulatorBase.cs Sat Jun 08 16:53:22 2013 +0000
97.3 @@ -0,0 +1,151 @@
97.4 +// --------------------------------------------------------------------------------------------------------------------
97.5 +// <copyright file="ManipulatorBase.cs" company="OxyPlot">
97.6 +// The MIT License (MIT)
97.7 +//
97.8 +// Copyright (c) 2012 Oystein Bjorke
97.9 +//
97.10 +// Permission is hereby granted, free of charge, to any person obtaining a
97.11 +// copy of this software and associated documentation files (the
97.12 +// "Software"), to deal in the Software without restriction, including
97.13 +// without limitation the rights to use, copy, modify, merge, publish,
97.14 +// distribute, sublicense, and/or sell copies of the Software, and to
97.15 +// permit persons to whom the Software is furnished to do so, subject to
97.16 +// the following conditions:
97.17 +//
97.18 +// The above copyright notice and this permission notice shall be included
97.19 +// in all copies or substantial portions of the Software.
97.20 +//
97.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
97.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
97.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
97.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
97.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
97.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
97.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
97.28 +// </copyright>
97.29 +// <summary>
97.30 +// The manipulator base.
97.31 +// </summary>
97.32 +// --------------------------------------------------------------------------------------------------------------------
97.33 +namespace OxyPlot
97.34 +{
97.35 + using OxyPlot.Axes;
97.36 +
97.37 + /// <summary>
97.38 + /// Provides an absract base class for plot control manipulators.
97.39 + /// </summary>
97.40 + public class ManipulatorBase
97.41 + {
97.42 + /// <summary>
97.43 + /// Initializes a new instance of the <see cref="ManipulatorBase"/> class.
97.44 + /// </summary>
97.45 + /// <param name="plotControl">
97.46 + /// The plot control.
97.47 + /// </param>
97.48 + protected ManipulatorBase(IPlotControl plotControl)
97.49 + {
97.50 + this.PlotControl = plotControl;
97.51 + }
97.52 +
97.53 + /// <summary>
97.54 + /// Gets the first position of the manipulation.
97.55 + /// </summary>
97.56 + public ScreenPoint StartPosition { get; private set; }
97.57 +
97.58 + /// <summary>
97.59 + /// Gets the plot control.
97.60 + /// </summary>
97.61 + protected IPlotControl PlotControl { get; private set; }
97.62 +
97.63 + /// <summary>
97.64 + /// Gets or sets the X axis.
97.65 + /// </summary>
97.66 + /// <value>The X axis.</value>
97.67 + protected Axis XAxis { get; set; }
97.68 +
97.69 + /// <summary>
97.70 + /// Gets or sets the Y axis.
97.71 + /// </summary>
97.72 + /// <value>The Y axis.</value>
97.73 + protected Axis YAxis { get; set; }
97.74 +
97.75 + /// <summary>
97.76 + /// Occurs when a manipulation is complete.
97.77 + /// </summary>
97.78 + /// <param name="e">
97.79 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
97.80 + /// </param>
97.81 + public virtual void Completed(ManipulationEventArgs e)
97.82 + {
97.83 + this.PlotControl.SetCursorType(CursorType.Default);
97.84 + }
97.85 +
97.86 + /// <summary>
97.87 + /// Occurs when the input device changes position during a manipulation.
97.88 + /// </summary>
97.89 + /// <param name="e">
97.90 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
97.91 + /// </param>
97.92 + public virtual void Delta(ManipulationEventArgs e)
97.93 + {
97.94 + }
97.95 +
97.96 + /// <summary>
97.97 + /// Gets the cursor for the manipulation.
97.98 + /// </summary>
97.99 + /// <returns>
97.100 + /// The cursor.
97.101 + /// </returns>
97.102 + public virtual CursorType GetCursorType()
97.103 + {
97.104 + return CursorType.Default;
97.105 + }
97.106 +
97.107 + /// <summary>
97.108 + /// Occurs when an input device begins a manipulation on the plot.
97.109 + /// </summary>
97.110 + /// <param name="e">
97.111 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
97.112 + /// </param>
97.113 + public virtual void Started(ManipulationEventArgs e)
97.114 + {
97.115 + Axis xaxis;
97.116 + Axis yaxis;
97.117 + this.PlotControl.GetAxesFromPoint(e.CurrentPosition, out xaxis, out yaxis);
97.118 + this.StartPosition = e.CurrentPosition;
97.119 +
97.120 + this.XAxis = xaxis;
97.121 + this.YAxis = yaxis;
97.122 +
97.123 + this.PlotControl.SetCursorType(this.GetCursorType());
97.124 + }
97.125 +
97.126 + /// <summary>
97.127 + /// Transforms a point from screen coordinates to data coordinates.
97.128 + /// </summary>
97.129 + /// <param name="x">
97.130 + /// The x coordinate.
97.131 + /// </param>
97.132 + /// <param name="y">
97.133 + /// The y coordinate.
97.134 + /// </param>
97.135 + /// <returns>
97.136 + /// A data point.
97.137 + /// </returns>
97.138 + protected DataPoint InverseTransform(double x, double y)
97.139 + {
97.140 + if (this.XAxis != null)
97.141 + {
97.142 + return this.XAxis.InverseTransform(x, y, this.YAxis);
97.143 + }
97.144 +
97.145 + if (this.YAxis != null)
97.146 + {
97.147 + return new DataPoint(0, this.YAxis.InverseTransform(y));
97.148 + }
97.149 +
97.150 + return new DataPoint();
97.151 + }
97.152 +
97.153 + }
97.154 +}
97.155 \ No newline at end of file
98.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
98.2 +++ b/External/OxyPlot/OxyPlot/Manipulators/PanManipulator.cs Sat Jun 08 16:53:22 2013 +0000
98.3 @@ -0,0 +1,100 @@
98.4 +// --------------------------------------------------------------------------------------------------------------------
98.5 +// <copyright file="PanManipulator.cs" company="OxyPlot">
98.6 +// The MIT License (MIT)
98.7 +//
98.8 +// Copyright (c) 2012 Oystein Bjorke
98.9 +//
98.10 +// Permission is hereby granted, free of charge, to any person obtaining a
98.11 +// copy of this software and associated documentation files (the
98.12 +// "Software"), to deal in the Software without restriction, including
98.13 +// without limitation the rights to use, copy, modify, merge, publish,
98.14 +// distribute, sublicense, and/or sell copies of the Software, and to
98.15 +// permit persons to whom the Software is furnished to do so, subject to
98.16 +// the following conditions:
98.17 +//
98.18 +// The above copyright notice and this permission notice shall be included
98.19 +// in all copies or substantial portions of the Software.
98.20 +//
98.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
98.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
98.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
98.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
98.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
98.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
98.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
98.28 +// </copyright>
98.29 +// <summary>
98.30 +// The pan manipulator.
98.31 +// </summary>
98.32 +// --------------------------------------------------------------------------------------------------------------------
98.33 +namespace OxyPlot
98.34 +{
98.35 + /// <summary>
98.36 + /// Provides a plot control manipulator for panning functionality.
98.37 + /// </summary>
98.38 + public class PanManipulator : ManipulatorBase
98.39 + {
98.40 + /// <summary>
98.41 + /// Initializes a new instance of the <see cref="PanManipulator"/> class.
98.42 + /// </summary>
98.43 + /// <param name="plotControl">
98.44 + /// The plot control.
98.45 + /// </param>
98.46 + public PanManipulator(IPlotControl plotControl)
98.47 + : base(plotControl)
98.48 + {
98.49 + }
98.50 +
98.51 + /// <summary>
98.52 + /// Gets or sets the previous position.
98.53 + /// </summary>
98.54 + private ScreenPoint PreviousPosition { get; set; }
98.55 +
98.56 + /// <summary>
98.57 + /// Occurs when the input device changes position during a manipulation.
98.58 + /// </summary>
98.59 + /// <param name="e">
98.60 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
98.61 + /// </param>
98.62 + public override void Delta(ManipulationEventArgs e)
98.63 + {
98.64 + base.Delta(e);
98.65 + if (this.XAxis != null)
98.66 + {
98.67 + this.PlotControl.Pan(this.XAxis, this.PreviousPosition, e.CurrentPosition);
98.68 + }
98.69 +
98.70 + if (this.YAxis != null)
98.71 + {
98.72 + this.PlotControl.Pan(this.YAxis, this.PreviousPosition, e.CurrentPosition);
98.73 + }
98.74 +
98.75 + this.PlotControl.RefreshPlot(false);
98.76 + this.PreviousPosition = e.CurrentPosition;
98.77 + }
98.78 +
98.79 + /// <summary>
98.80 + /// Gets the cursor for the manipulation.
98.81 + /// </summary>
98.82 + /// <returns>
98.83 + /// The cursor.
98.84 + /// </returns>
98.85 + public override CursorType GetCursorType()
98.86 + {
98.87 + return CursorType.Pan;
98.88 + }
98.89 +
98.90 + /// <summary>
98.91 + /// Occurs when an input device begins a manipulation on the plot.
98.92 + /// </summary>
98.93 + /// <param name="e">
98.94 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
98.95 + /// </param>
98.96 + public override void Started(ManipulationEventArgs e)
98.97 + {
98.98 + base.Started(e);
98.99 + this.PreviousPosition = e.CurrentPosition;
98.100 + }
98.101 +
98.102 + }
98.103 +}
98.104 \ No newline at end of file
99.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
99.2 +++ b/External/OxyPlot/OxyPlot/Manipulators/ResetManipulator.cs Sat Jun 08 16:53:22 2013 +0000
99.3 @@ -0,0 +1,71 @@
99.4 +// --------------------------------------------------------------------------------------------------------------------
99.5 +// <copyright file="ResetManipulator.cs" company="OxyPlot">
99.6 +// The MIT License (MIT)
99.7 +//
99.8 +// Copyright (c) 2012 Oystein Bjorke
99.9 +//
99.10 +// Permission is hereby granted, free of charge, to any person obtaining a
99.11 +// copy of this software and associated documentation files (the
99.12 +// "Software"), to deal in the Software without restriction, including
99.13 +// without limitation the rights to use, copy, modify, merge, publish,
99.14 +// distribute, sublicense, and/or sell copies of the Software, and to
99.15 +// permit persons to whom the Software is furnished to do so, subject to
99.16 +// the following conditions:
99.17 +//
99.18 +// The above copyright notice and this permission notice shall be included
99.19 +// in all copies or substantial portions of the Software.
99.20 +//
99.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
99.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
99.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
99.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
99.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
99.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
99.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
99.28 +// </copyright>
99.29 +// <summary>
99.30 +// The reset manipulator.
99.31 +// </summary>
99.32 +// --------------------------------------------------------------------------------------------------------------------
99.33 +namespace OxyPlot
99.34 +{
99.35 + /// <summary>
99.36 + /// Provides a plot control manipulator for reset functionality.
99.37 + /// </summary>
99.38 + public class ResetManipulator : ManipulatorBase
99.39 + {
99.40 + /// <summary>
99.41 + /// Initializes a new instance of the <see cref="ResetManipulator"/> class.
99.42 + /// </summary>
99.43 + /// <param name="plotControl">
99.44 + /// The plot control.
99.45 + /// </param>
99.46 + public ResetManipulator(IPlotControl plotControl)
99.47 + : base(plotControl)
99.48 + {
99.49 + }
99.50 +
99.51 + /// <summary>
99.52 + /// Occurs when an input device begins a manipulation on the plot.
99.53 + /// </summary>
99.54 + /// <param name="e">
99.55 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
99.56 + /// </param>
99.57 + public override void Started(ManipulationEventArgs e)
99.58 + {
99.59 + base.Started(e);
99.60 + if (this.XAxis != null)
99.61 + {
99.62 + this.PlotControl.Reset(this.XAxis);
99.63 + }
99.64 +
99.65 + if (this.YAxis != null)
99.66 + {
99.67 + this.PlotControl.Reset(this.YAxis);
99.68 + }
99.69 +
99.70 + this.PlotControl.InvalidatePlot();
99.71 + }
99.72 +
99.73 + }
99.74 +}
99.75 \ No newline at end of file
100.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
100.2 +++ b/External/OxyPlot/OxyPlot/Manipulators/TrackerHitResult.cs Sat Jun 08 16:53:22 2013 +0000
100.3 @@ -0,0 +1,162 @@
100.4 +// --------------------------------------------------------------------------------------------------------------------
100.5 +// <copyright file="TrackerHitResult.cs" company="OxyPlot">
100.6 +// The MIT License (MIT)
100.7 +//
100.8 +// Copyright (c) 2012 Oystein Bjorke
100.9 +//
100.10 +// Permission is hereby granted, free of charge, to any person obtaining a
100.11 +// copy of this software and associated documentation files (the
100.12 +// "Software"), to deal in the Software without restriction, including
100.13 +// without limitation the rights to use, copy, modify, merge, publish,
100.14 +// distribute, sublicense, and/or sell copies of the Software, and to
100.15 +// permit persons to whom the Software is furnished to do so, subject to
100.16 +// the following conditions:
100.17 +//
100.18 +// The above copyright notice and this permission notice shall be included
100.19 +// in all copies or substantial portions of the Software.
100.20 +//
100.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
100.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
100.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
100.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
100.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
100.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
100.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
100.28 +// </copyright>
100.29 +// <summary>
100.30 +// Provides a data container for a tracker hit result.
100.31 +// </summary>
100.32 +// --------------------------------------------------------------------------------------------------------------------
100.33 +namespace OxyPlot
100.34 +{
100.35 + using OxyPlot.Series;
100.36 +
100.37 + /// <summary>
100.38 + /// Provides a data container for a tracker hit result.
100.39 + /// </summary>
100.40 + /// <remarks>
100.41 + /// This is used as DataContext for the TrackerControl.
100.42 + /// The TrackerControl is visible when the user use the left mouse button to "track" points on the series.
100.43 + /// </remarks>
100.44 + public class TrackerHitResult
100.45 + {
100.46 + /// <summary>
100.47 + /// The default format string.
100.48 + /// </summary>
100.49 + private const string DefaultFormatString = "{0}\n{1}: {2}\n{3}: {4}";
100.50 +
100.51 + /// <summary>
100.52 + /// Initializes a new instance of the <see cref="TrackerHitResult"/> class.
100.53 + /// </summary>
100.54 + /// <param name="series">The series.</param>
100.55 + /// <param name="dp">The data point.</param>
100.56 + /// <param name="sp">The screen point.</param>
100.57 + /// <param name="item">The item.</param>
100.58 + /// <param name="index">The index.</param>
100.59 + /// <param name="text">The text.</param>
100.60 + public TrackerHitResult(OxyPlot.Series.Series series, IDataPoint dp, ScreenPoint sp, object item = null, double index = -1, string text = null)
100.61 + {
100.62 + this.DataPoint = dp;
100.63 + this.Position = sp;
100.64 + this.Item = item;
100.65 + this.Index = index;
100.66 + this.Series = series;
100.67 + this.Text = text;
100.68 + var ds = series as DataPointSeries;
100.69 + if (ds != null)
100.70 + {
100.71 + this.XAxis = ds.XAxis;
100.72 + this.YAxis = ds.YAxis;
100.73 + }
100.74 + }
100.75 +
100.76 + /// <summary>
100.77 + /// Gets or sets the nearest or interpolated data point.
100.78 + /// </summary>
100.79 + public IDataPoint DataPoint { get; set; }
100.80 +
100.81 + /// <summary>
100.82 + /// Gets or sets the source item of the point.
100.83 + /// If the current point is from an ItemsSource and is not interpolated, this property will contain the item.
100.84 + /// </summary>
100.85 + public object Item { get; set; }
100.86 +
100.87 + /// <summary>
100.88 + /// Gets or sets the index for the Item.
100.89 + /// </summary>
100.90 + public double Index { get; set; }
100.91 +
100.92 + /// <summary>
100.93 + /// Gets or sets the horizontal/vertical line extents.
100.94 + /// </summary>
100.95 + public OxyRect LineExtents { get; set; }
100.96 +
100.97 + /// <summary>
100.98 + /// Gets or sets the plot model.
100.99 + /// </summary>
100.100 + public PlotModel PlotModel { get; set; }
100.101 +
100.102 + /// <summary>
100.103 + /// Gets or sets the position in screen coordinates.
100.104 + /// </summary>
100.105 + public ScreenPoint Position { get; set; }
100.106 +
100.107 + /// <summary>
100.108 + /// Gets or sets the series that is being tracked.
100.109 + /// </summary>
100.110 + public Series.Series Series { get; set; }
100.111 +
100.112 + /// <summary>
100.113 + /// Gets or sets the text shown in the tracker.
100.114 + /// </summary>
100.115 + public string Text { get; set; }
100.116 +
100.117 + /// <summary>
100.118 + /// Gets or sets the X axis.
100.119 + /// </summary>
100.120 + public Axes.Axis XAxis { get; set; }
100.121 +
100.122 + /// <summary>
100.123 + /// Gets or sets the Y axis.
100.124 + /// </summary>
100.125 + public Axes.Axis YAxis { get; set; }
100.126 +
100.127 + /// <summary>
100.128 + /// Returns a <see cref="System.String"/> that represents this instance.
100.129 + /// </summary>
100.130 + /// <returns>
100.131 + /// A <see cref="System.String"/> that represents this instance.
100.132 + /// </returns>
100.133 + public override string ToString()
100.134 + {
100.135 + if (this.Text != null)
100.136 + {
100.137 + return this.Text;
100.138 + }
100.139 +
100.140 + var ts = this.Series as ITrackableSeries;
100.141 + string formatString = DefaultFormatString;
100.142 + if (ts != null && !string.IsNullOrEmpty(ts.TrackerFormatString))
100.143 + {
100.144 + formatString = ts.TrackerFormatString;
100.145 + }
100.146 +
100.147 + string xaxisTitle = (this.XAxis != null ? this.XAxis.Title : null) ?? "X";
100.148 + string yaxisTitle = (this.YAxis != null ? this.YAxis.Title : null) ?? "Y";
100.149 + object xvalue = this.XAxis != null ? this.XAxis.GetValue(this.DataPoint.X) : this.DataPoint.X;
100.150 + object yvalue = this.YAxis != null ? this.YAxis.GetValue(this.DataPoint.Y) : this.DataPoint.Y;
100.151 +
100.152 + return StringHelper.Format(
100.153 + this.Series.ActualCulture,
100.154 + formatString,
100.155 + this.Item,
100.156 + this.Series.Title,
100.157 + xaxisTitle,
100.158 + xvalue,
100.159 + yaxisTitle,
100.160 + yvalue,
100.161 + this.Item).Trim();
100.162 + }
100.163 +
100.164 + }
100.165 +}
100.166 \ No newline at end of file
101.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
101.2 +++ b/External/OxyPlot/OxyPlot/Manipulators/TrackerManipulator.cs Sat Jun 08 16:53:22 2013 +0000
101.3 @@ -0,0 +1,186 @@
101.4 +// --------------------------------------------------------------------------------------------------------------------
101.5 +// <copyright file="TrackerManipulator.cs" company="OxyPlot">
101.6 +// The MIT License (MIT)
101.7 +//
101.8 +// Copyright (c) 2012 Oystein Bjorke
101.9 +//
101.10 +// Permission is hereby granted, free of charge, to any person obtaining a
101.11 +// copy of this software and associated documentation files (the
101.12 +// "Software"), to deal in the Software without restriction, including
101.13 +// without limitation the rights to use, copy, modify, merge, publish,
101.14 +// distribute, sublicense, and/or sell copies of the Software, and to
101.15 +// permit persons to whom the Software is furnished to do so, subject to
101.16 +// the following conditions:
101.17 +//
101.18 +// The above copyright notice and this permission notice shall be included
101.19 +// in all copies or substantial portions of the Software.
101.20 +//
101.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
101.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
101.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
101.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
101.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
101.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
101.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
101.28 +// </copyright>
101.29 +// <summary>
101.30 +// The tracker manipulator.
101.31 +// </summary>
101.32 +// --------------------------------------------------------------------------------------------------------------------
101.33 +namespace OxyPlot
101.34 +{
101.35 + using OxyPlot.Series;
101.36 +
101.37 + /// <summary>
101.38 + /// Provides a plot control manipulator for tracker functionality.
101.39 + /// </summary>
101.40 + public class TrackerManipulator : ManipulatorBase
101.41 + {
101.42 + /// <summary>
101.43 + /// The current series.
101.44 + /// </summary>
101.45 + private ITrackableSeries currentSeries;
101.46 +
101.47 + /// <summary>
101.48 + /// Initializes a new instance of the <see cref="TrackerManipulator"/> class.
101.49 + /// </summary>
101.50 + /// <param name="plotControl">
101.51 + /// The plot control.
101.52 + /// </param>
101.53 + public TrackerManipulator(IPlotControl plotControl)
101.54 + : base(plotControl)
101.55 + {
101.56 + this.Snap = true;
101.57 + this.PointsOnly = false;
101.58 + }
101.59 +
101.60 + /// <summary>
101.61 + /// Gets or sets a value indicating whether to show tracker on points only (not interpolating).
101.62 + /// </summary>
101.63 + public bool PointsOnly { get; set; }
101.64 +
101.65 + /// <summary>
101.66 + /// Gets or sets a value indicating whether to snap to the nearest point.
101.67 + /// </summary>
101.68 + public bool Snap { get; set; }
101.69 +
101.70 + /// <summary>
101.71 + /// Occurs when a manipulation is complete.
101.72 + /// </summary>
101.73 + /// <param name="e">
101.74 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
101.75 + /// </param>
101.76 + public override void Completed(ManipulationEventArgs e)
101.77 + {
101.78 + base.Completed(e);
101.79 +
101.80 + if (this.currentSeries == null)
101.81 + {
101.82 + return;
101.83 + }
101.84 +
101.85 + this.currentSeries = null;
101.86 + this.PlotControl.HideTracker();
101.87 + }
101.88 +
101.89 + /// <summary>
101.90 + /// Occurs when the input device changes position during a manipulation.
101.91 + /// </summary>
101.92 + /// <param name="e">
101.93 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
101.94 + /// </param>
101.95 + public override void Delta(ManipulationEventArgs e)
101.96 + {
101.97 + base.Delta(e);
101.98 + if (this.currentSeries == null)
101.99 + {
101.100 + return;
101.101 + }
101.102 +
101.103 + if (!this.PlotControl.ActualModel.PlotArea.Contains(e.CurrentPosition.X, e.CurrentPosition.Y))
101.104 + {
101.105 + return;
101.106 + }
101.107 +
101.108 + TrackerHitResult result = GetNearestHit(this.currentSeries, e.CurrentPosition, this.Snap, this.PointsOnly);
101.109 + if (result != null)
101.110 + {
101.111 + result.PlotModel = this.PlotControl.ActualModel;
101.112 + this.PlotControl.ShowTracker(result);
101.113 + }
101.114 + }
101.115 +
101.116 + /// <summary>
101.117 + /// Gets the cursor for the manipulation.
101.118 + /// </summary>
101.119 + /// <returns>
101.120 + /// The cursor.
101.121 + /// </returns>
101.122 + public override CursorType GetCursorType()
101.123 + {
101.124 + return CursorType.Default;
101.125 + }
101.126 +
101.127 + /// <summary>
101.128 + /// Occurs when an input device begins a manipulation on the plot.
101.129 + /// </summary>
101.130 + /// <param name="e">
101.131 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
101.132 + /// </param>
101.133 + public override void Started(ManipulationEventArgs e)
101.134 + {
101.135 + base.Started(e);
101.136 + this.currentSeries = this.PlotControl.GetSeriesFromPoint(e.CurrentPosition);
101.137 + this.Delta(e);
101.138 + }
101.139 +
101.140 + /// <summary>
101.141 + /// Gets the nearest tracker hit.
101.142 + /// </summary>
101.143 + /// <param name="s">
101.144 + /// The series.
101.145 + /// </param>
101.146 + /// <param name="point">
101.147 + /// The point.
101.148 + /// </param>
101.149 + /// <param name="snap">
101.150 + /// Snap to points.
101.151 + /// </param>
101.152 + /// <param name="pointsOnly">
101.153 + /// Check points only (no interpolation).
101.154 + /// </param>
101.155 + /// <returns>
101.156 + /// A tracker hit result.
101.157 + /// </returns>
101.158 + private static TrackerHitResult GetNearestHit(ITrackableSeries s, ScreenPoint point, bool snap, bool pointsOnly)
101.159 + {
101.160 + if (s == null)
101.161 + {
101.162 + return null;
101.163 + }
101.164 +
101.165 + // Check data points only
101.166 + if (snap || pointsOnly)
101.167 + {
101.168 + TrackerHitResult result = s.GetNearestPoint(point, false);
101.169 + if (result != null)
101.170 + {
101.171 + if (result.Position.DistanceTo(point) < 20)
101.172 + {
101.173 + return result;
101.174 + }
101.175 + }
101.176 + }
101.177 +
101.178 + // Check between data points (if possible)
101.179 + if (!pointsOnly)
101.180 + {
101.181 + TrackerHitResult result = s.GetNearestPoint(point, true);
101.182 + return result;
101.183 + }
101.184 +
101.185 + return null;
101.186 + }
101.187 +
101.188 + }
101.189 +}
101.190 \ No newline at end of file
102.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
102.2 +++ b/External/OxyPlot/OxyPlot/Manipulators/ZoomManipulator.cs Sat Jun 08 16:53:22 2013 +0000
102.3 @@ -0,0 +1,72 @@
102.4 +// --------------------------------------------------------------------------------------------------------------------
102.5 +// <copyright file="ZoomManipulator.cs" company="OxyPlot">
102.6 +// The MIT License (MIT)
102.7 +//
102.8 +// Copyright (c) 2012 Oystein Bjorke
102.9 +//
102.10 +// Permission is hereby granted, free of charge, to any person obtaining a
102.11 +// copy of this software and associated documentation files (the
102.12 +// "Software"), to deal in the Software without restriction, including
102.13 +// without limitation the rights to use, copy, modify, merge, publish,
102.14 +// distribute, sublicense, and/or sell copies of the Software, and to
102.15 +// permit persons to whom the Software is furnished to do so, subject to
102.16 +// the following conditions:
102.17 +//
102.18 +// The above copyright notice and this permission notice shall be included
102.19 +// in all copies or substantial portions of the Software.
102.20 +//
102.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
102.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
102.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
102.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
102.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
102.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
102.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
102.28 +// </copyright>
102.29 +// <summary>
102.30 +// The zoom manipulator.
102.31 +// </summary>
102.32 +// --------------------------------------------------------------------------------------------------------------------
102.33 +namespace OxyPlot
102.34 +{
102.35 + /// <summary>
102.36 + /// Provides a plot control manipulator for zoom functionality.
102.37 + /// </summary>
102.38 + public class ZoomManipulator : ManipulatorBase
102.39 + {
102.40 + /// <summary>
102.41 + /// Initializes a new instance of the <see cref="ZoomManipulator"/> class.
102.42 + /// </summary>
102.43 + /// <param name="plotControl">
102.44 + /// The plot control.
102.45 + /// </param>
102.46 + public ZoomManipulator(IPlotControl plotControl)
102.47 + : base(plotControl)
102.48 + {
102.49 + }
102.50 +
102.51 + /// <summary>
102.52 + /// Occurs when the input device changes position during a manipulation.
102.53 + /// </summary>
102.54 + /// <param name="e">The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.</param>
102.55 + public override void Delta(ManipulationEventArgs e)
102.56 + {
102.57 + base.Delta(e);
102.58 +
102.59 + DataPoint current = this.InverseTransform(e.CurrentPosition.X, e.CurrentPosition.Y);
102.60 +
102.61 + if (this.XAxis != null)
102.62 + {
102.63 + this.PlotControl.ZoomAt(this.XAxis, e.ScaleX, current.X);
102.64 + }
102.65 +
102.66 + if (this.YAxis != null)
102.67 + {
102.68 + this.PlotControl.ZoomAt(this.YAxis, e.ScaleY, current.Y);
102.69 + }
102.70 +
102.71 + this.PlotControl.InvalidatePlot();
102.72 + }
102.73 +
102.74 + }
102.75 +}
102.76 \ No newline at end of file
103.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
103.2 +++ b/External/OxyPlot/OxyPlot/Manipulators/ZoomRectangleManipulator.cs Sat Jun 08 16:53:22 2013 +0000
103.3 @@ -0,0 +1,154 @@
103.4 +// --------------------------------------------------------------------------------------------------------------------
103.5 +// <copyright file="ZoomRectangleManipulator.cs" company="OxyPlot">
103.6 +// The MIT License (MIT)
103.7 +//
103.8 +// Copyright (c) 2012 Oystein Bjorke
103.9 +//
103.10 +// Permission is hereby granted, free of charge, to any person obtaining a
103.11 +// copy of this software and associated documentation files (the
103.12 +// "Software"), to deal in the Software without restriction, including
103.13 +// without limitation the rights to use, copy, modify, merge, publish,
103.14 +// distribute, sublicense, and/or sell copies of the Software, and to
103.15 +// permit persons to whom the Software is furnished to do so, subject to
103.16 +// the following conditions:
103.17 +//
103.18 +// The above copyright notice and this permission notice shall be included
103.19 +// in all copies or substantial portions of the Software.
103.20 +//
103.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
103.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
103.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
103.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
103.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
103.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
103.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
103.28 +// </copyright>
103.29 +// <summary>
103.30 +// The zoom manipulator.
103.31 +// </summary>
103.32 +// --------------------------------------------------------------------------------------------------------------------
103.33 +namespace OxyPlot
103.34 +{
103.35 + using System;
103.36 +
103.37 + /// <summary>
103.38 + /// Provides a plot control manipulator for zoom by rectangle functionality.
103.39 + /// </summary>
103.40 + public class ZoomRectangleManipulator : ManipulatorBase
103.41 + {
103.42 + /// <summary>
103.43 + /// Initializes a new instance of the <see cref="ZoomRectangleManipulator"/> class.
103.44 + /// </summary>
103.45 + /// <param name="plotControl">
103.46 + /// The plot control.
103.47 + /// </param>
103.48 + public ZoomRectangleManipulator(IPlotControl plotControl)
103.49 + : base(plotControl)
103.50 + {
103.51 + }
103.52 +
103.53 + /// <summary>
103.54 + /// Gets or sets the zoom rectangle.
103.55 + /// </summary>
103.56 + private OxyRect ZoomRectangle { get; set; }
103.57 +
103.58 + /// <summary>
103.59 + /// Occurs when a manipulation is complete.
103.60 + /// </summary>
103.61 + /// <param name="e">
103.62 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
103.63 + /// </param>
103.64 + public override void Completed(ManipulationEventArgs e)
103.65 + {
103.66 + base.Completed(e);
103.67 +
103.68 + this.PlotControl.HideZoomRectangle();
103.69 +
103.70 + if (this.ZoomRectangle.Width > 10 && this.ZoomRectangle.Height > 10)
103.71 + {
103.72 + DataPoint p0 = this.InverseTransform(this.ZoomRectangle.Left, this.ZoomRectangle.Top);
103.73 + DataPoint p1 = this.InverseTransform(this.ZoomRectangle.Right, this.ZoomRectangle.Bottom);
103.74 +
103.75 + if (this.XAxis != null)
103.76 + {
103.77 + this.PlotControl.Zoom(this.XAxis, p0.X, p1.X);
103.78 + }
103.79 +
103.80 + if (this.YAxis != null)
103.81 + {
103.82 + this.PlotControl.Zoom(this.YAxis, p0.Y, p1.Y);
103.83 + }
103.84 +
103.85 + this.PlotControl.InvalidatePlot();
103.86 + }
103.87 + }
103.88 +
103.89 + /// <summary>
103.90 + /// Occurs when the input device changes position during a manipulation.
103.91 + /// </summary>
103.92 + /// <param name="e">
103.93 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
103.94 + /// </param>
103.95 + public override void Delta(ManipulationEventArgs e)
103.96 + {
103.97 + base.Delta(e);
103.98 +
103.99 + OxyRect plotArea = this.PlotControl.ActualModel.PlotArea;
103.100 +
103.101 + double x = Math.Min(this.StartPosition.X, e.CurrentPosition.X);
103.102 + double w = Math.Abs(this.StartPosition.X - e.CurrentPosition.X);
103.103 + double y = Math.Min(this.StartPosition.Y, e.CurrentPosition.Y);
103.104 + double h = Math.Abs(this.StartPosition.Y - e.CurrentPosition.Y);
103.105 +
103.106 + if (this.XAxis == null)
103.107 + {
103.108 + x = plotArea.Left;
103.109 + w = plotArea.Width;
103.110 + }
103.111 +
103.112 + if (this.YAxis == null)
103.113 + {
103.114 + y = plotArea.Top;
103.115 + h = plotArea.Height;
103.116 + }
103.117 +
103.118 + this.ZoomRectangle = new OxyRect(x, y, w, h);
103.119 + this.PlotControl.ShowZoomRectangle(this.ZoomRectangle);
103.120 + }
103.121 +
103.122 + /// <summary>
103.123 + /// Gets the cursor for the manipulation.
103.124 + /// </summary>
103.125 + /// <returns>
103.126 + /// The cursor.
103.127 + /// </returns>
103.128 + public override CursorType GetCursorType()
103.129 + {
103.130 + if (this.XAxis == null)
103.131 + {
103.132 + return CursorType.ZoomVertical;
103.133 + }
103.134 +
103.135 + if (this.YAxis == null)
103.136 + {
103.137 + return CursorType.ZoomHorizontal;
103.138 + }
103.139 +
103.140 + return CursorType.ZoomRectangle;
103.141 + }
103.142 +
103.143 + /// <summary>
103.144 + /// Occurs when an input device begins a manipulation on the plot.
103.145 + /// </summary>
103.146 + /// <param name="e">
103.147 + /// The <see cref="OxyPlot.ManipulationEventArgs"/> instance containing the event data.
103.148 + /// </param>
103.149 + public override void Started(ManipulationEventArgs e)
103.150 + {
103.151 + base.Started(e);
103.152 + this.ZoomRectangle = new OxyRect(this.StartPosition.X, this.StartPosition.Y, 0, 0);
103.153 + this.PlotControl.ShowZoomRectangle(this.ZoomRectangle);
103.154 + }
103.155 +
103.156 + }
103.157 +}
103.158 \ No newline at end of file
104.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
104.2 +++ b/External/OxyPlot/OxyPlot/Manipulators/ZoomStepManipulator.cs Sat Jun 08 16:53:22 2013 +0000
104.3 @@ -0,0 +1,106 @@
104.4 +// --------------------------------------------------------------------------------------------------------------------
104.5 +// <copyright file="ZoomStepManipulator.cs" company="OxyPlot">
104.6 +// The MIT License (MIT)
104.7 +//
104.8 +// Copyright (c) 2012 Oystein Bjorke
104.9 +//
104.10 +// Permission is hereby granted, free of charge, to any person obtaining a
104.11 +// copy of this software and associated documentation files (the
104.12 +// "Software"), to deal in the Software without restriction, including
104.13 +// without limitation the rights to use, copy, modify, merge, publish,
104.14 +// distribute, sublicense, and/or sell copies of the Software, and to
104.15 +// permit persons to whom the Software is furnished to do so, subject to
104.16 +// the following conditions:
104.17 +//
104.18 +// The above copyright notice and this permission notice shall be included
104.19 +// in all copies or substantial portions of the Software.
104.20 +//
104.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
104.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
104.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
104.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
104.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
104.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
104.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
104.28 +// </copyright>
104.29 +// <summary>
104.30 +// The step manipulator.
104.31 +// </summary>
104.32 +// --------------------------------------------------------------------------------------------------------------------
104.33 +namespace OxyPlot
104.34 +{
104.35 + /// <summary>
104.36 + /// Provides a plot control manipulator for stepwise zoom functionality.
104.37 + /// </summary>
104.38 + public class ZoomStepManipulator : ManipulatorBase
104.39 + {
104.40 + /// <summary>
104.41 + /// Initializes a new instance of the <see cref="ZoomStepManipulator"/> class.
104.42 + /// </summary>
104.43 + /// <param name="plotControl">
104.44 + /// The plot control.
104.45 + /// </param>
104.46 + /// <param name="step">
104.47 + /// The step.
104.48 + /// </param>
104.49 + /// <param name="fineControl">
104.50 + /// The fine Control.
104.51 + /// </param>
104.52 + public ZoomStepManipulator(IPlotControl plotControl, double step, bool fineControl)
104.53 + : base(plotControl)
104.54 + {
104.55 + this.Step = step;
104.56 + this.FineControl = fineControl;
104.57 + }
104.58 +
104.59 + /// <summary>
104.60 + /// Gets or sets a value indicating whether FineControl.
104.61 + /// </summary>
104.62 + public bool FineControl { get; set; }
104.63 +
104.64 + /// <summary>
104.65 + /// Gets or sets Step.
104.66 + /// </summary>
104.67 + public double Step { get; set; }
104.68 +
104.69 + /// <summary>
104.70 + /// The started.
104.71 + /// </summary>
104.72 + /// <param name="e">
104.73 + /// The e.
104.74 + /// </param>
104.75 + public override void Started(ManipulationEventArgs e)
104.76 + {
104.77 + base.Started(e);
104.78 +
104.79 + DataPoint current = this.InverseTransform(e.CurrentPosition.X, e.CurrentPosition.Y);
104.80 +
104.81 + double scale = this.Step;
104.82 + if (this.FineControl)
104.83 + {
104.84 + scale *= 3;
104.85 + }
104.86 +
104.87 + scale = 1 + scale;
104.88 +
104.89 + // make sure the zoom factor is not negative
104.90 + if (scale < 0.1)
104.91 + {
104.92 + scale = 0.1;
104.93 + }
104.94 +
104.95 + if (this.XAxis != null)
104.96 + {
104.97 + this.PlotControl.ZoomAt(this.XAxis, scale, current.X);
104.98 + }
104.99 +
104.100 + if (this.YAxis != null)
104.101 + {
104.102 + this.PlotControl.ZoomAt(this.YAxis, scale, current.Y);
104.103 + }
104.104 +
104.105 + this.PlotControl.InvalidatePlot();
104.106 + }
104.107 +
104.108 + }
104.109 +}
104.110 \ No newline at end of file
105.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
105.2 +++ b/External/OxyPlot/OxyPlot/MouseActions/MouseAction.cs Sat Jun 08 16:53:22 2013 +0000
105.3 @@ -0,0 +1,54 @@
105.4 +// --------------------------------------------------------------------------------------------------------------------
105.5 +// <copyright file="MouseAction.cs" company="OxyPlot">
105.6 +// The MIT License (MIT)
105.7 +//
105.8 +// Copyright (c) 2012 Oystein Bjorke
105.9 +//
105.10 +// Permission is hereby granted, free of charge, to any person obtaining a
105.11 +// copy of this software and associated documentation files (the
105.12 +// "Software"), to deal in the Software without restriction, including
105.13 +// without limitation the rights to use, copy, modify, merge, publish,
105.14 +// distribute, sublicense, and/or sell copies of the Software, and to
105.15 +// permit persons to whom the Software is furnished to do so, subject to
105.16 +// the following conditions:
105.17 +//
105.18 +// The above copyright notice and this permission notice shall be included
105.19 +// in all copies or substantial portions of the Software.
105.20 +//
105.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
105.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
105.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
105.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
105.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
105.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
105.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
105.28 +// </copyright>
105.29 +// --------------------------------------------------------------------------------------------------------------------
105.30 +namespace OxyPlot
105.31 +{
105.32 + public abstract class MouseAction : IMouseAction
105.33 + {
105.34 + protected IPlotControl pc;
105.35 +
105.36 + protected MouseAction(IPlotControl pc)
105.37 + {
105.38 + this.pc = pc;
105.39 + }
105.40 +
105.41 + public virtual void OnMouseDown(ScreenPoint pt, OxyMouseButton button, int clickCount, bool control, bool shift, bool alt)
105.42 + {
105.43 + }
105.44 +
105.45 + public virtual void OnMouseMove(ScreenPoint pt, bool control, bool shift, bool alt)
105.46 + {
105.47 + }
105.48 +
105.49 + public virtual void OnMouseUp()
105.50 + {
105.51 + }
105.52 +
105.53 + public virtual void OnMouseWheel(ScreenPoint pt, double delta, bool control, bool shift, bool alt)
105.54 + {
105.55 + }
105.56 + }
105.57 +}
105.58 \ No newline at end of file
106.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
106.2 +++ b/External/OxyPlot/OxyPlot/MouseActions/SliderAction.cs Sat Jun 08 16:53:22 2013 +0000
106.3 @@ -0,0 +1,106 @@
106.4 +// --------------------------------------------------------------------------------------------------------------------
106.5 +// <copyright file="SliderAction.cs" company="OxyPlot">
106.6 +// The MIT License (MIT)
106.7 +//
106.8 +// Copyright (c) 2012 Oystein Bjorke
106.9 +//
106.10 +// Permission is hereby granted, free of charge, to any person obtaining a
106.11 +// copy of this software and associated documentation files (the
106.12 +// "Software"), to deal in the Software without restriction, including
106.13 +// without limitation the rights to use, copy, modify, merge, publish,
106.14 +// distribute, sublicense, and/or sell copies of the Software, and to
106.15 +// permit persons to whom the Software is furnished to do so, subject to
106.16 +// the following conditions:
106.17 +//
106.18 +// The above copyright notice and this permission notice shall be included
106.19 +// in all copies or substantial portions of the Software.
106.20 +//
106.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
106.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
106.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
106.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
106.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
106.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
106.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
106.28 +// </copyright>
106.29 +// --------------------------------------------------------------------------------------------------------------------
106.30 +namespace OxyPlot
106.31 +{
106.32 + // todo: use screen coordinates instead of original points (problem on log axes)
106.33 + public class SliderAction : MouseAction
106.34 + {
106.35 + public SliderAction(IPlot pc)
106.36 + : base(pc)
106.37 + {
106.38 + }
106.39 +
106.40 + private DataSeries currentSeries;
106.41 +
106.42 + public override void OnMouseDown(ScreenPoint pt, OxyMouseButton button, int clickCount, bool control, bool shift)
106.43 + {
106.44 + base.OnMouseDown(pt, button, clickCount, control, shift);
106.45 +
106.46 + if (button != OxyMouseButton.Left)
106.47 + return;
106.48 +
106.49 + // Middle button double click adds an annotation
106.50 + if (clickCount == 2)
106.51 + {
106.52 + // pc.Annotations.
106.53 + pc.Refresh();
106.54 + }
106.55 +
106.56 + currentSeries = pc.GetSeriesFromPoint(pt) as DataSeries;
106.57 +
106.58 + OnMouseMove(pt, control, shift);
106.59 +
106.60 + //pc.CaptureMouse();
106.61 + // pc.Cursor = Cursors.Cross;
106.62 + }
106.63 +
106.64 + public override void OnMouseMove(ScreenPoint pt, bool control, bool shift)
106.65 + {
106.66 + if (currentSeries == null)
106.67 + return;
106.68 +
106.69 + var current = GetNearestPoint(currentSeries, pt, !control, shift);
106.70 + if (current != null)
106.71 + pc.ShowSlider(currentSeries, current.Value);
106.72 + }
106.73 +
106.74 + private static DataPoint? GetNearestPoint(ISeries s, ScreenPoint point, bool snap, bool pointsOnly)
106.75 + {
106.76 + if (s == null)
106.77 + return null;
106.78 +
106.79 + if (snap || pointsOnly)
106.80 + {
106.81 + ScreenPoint spn;
106.82 + DataPoint dpn;
106.83 + if (s.GetNearestPoint(point, out dpn, out spn) && snap)
106.84 + {
106.85 + if (spn.DistanceTo(point) < 20)
106.86 + return dpn;
106.87 + }
106.88 + }
106.89 +
106.90 + ScreenPoint sp;
106.91 + DataPoint dp;
106.92 +
106.93 + if (!pointsOnly)
106.94 + if (s.GetNearestInterpolatedPoint(point, out dp, out sp))
106.95 + return dp;
106.96 +
106.97 + return null;
106.98 + }
106.99 +
106.100 + public override void OnMouseUp()
106.101 + {
106.102 + base.OnMouseUp();
106.103 + if (currentSeries == null)
106.104 + return;
106.105 + currentSeries = null;
106.106 + pc.HideSlider();
106.107 + }
106.108 + }
106.109 +}
106.110 \ No newline at end of file
107.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
107.2 +++ b/External/OxyPlot/OxyPlot/NamespaceDoc.cs Sat Jun 08 16:53:22 2013 +0000
107.3 @@ -0,0 +1,37 @@
107.4 +// --------------------------------------------------------------------------------------------------------------------
107.5 +// <copyright file="NamespaceDoc.cs" company="OxyPlot">
107.6 +// The MIT License (MIT)
107.7 +//
107.8 +// Copyright (c) 2012 Oystein Bjorke
107.9 +//
107.10 +// Permission is hereby granted, free of charge, to any person obtaining a
107.11 +// copy of this software and associated documentation files (the
107.12 +// "Software"), to deal in the Software without restriction, including
107.13 +// without limitation the rights to use, copy, modify, merge, publish,
107.14 +// distribute, sublicense, and/or sell copies of the Software, and to
107.15 +// permit persons to whom the Software is furnished to do so, subject to
107.16 +// the following conditions:
107.17 +//
107.18 +// The above copyright notice and this permission notice shall be included
107.19 +// in all copies or substantial portions of the Software.
107.20 +//
107.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
107.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
107.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
107.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
107.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
107.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
107.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
107.28 +// </copyright>
107.29 +// --------------------------------------------------------------------------------------------------------------------
107.30 +
107.31 +namespace OxyPlot
107.32 +{
107.33 + /// <summary>
107.34 + /// The OxyPlot namespace contains the platform independent classes of the library.
107.35 + /// </summary>
107.36 + [System.Runtime.CompilerServices.CompilerGenerated]
107.37 + internal class NamespaceDoc
107.38 + {
107.39 + }
107.40 +}
107.41 \ No newline at end of file
108.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
108.2 +++ b/External/OxyPlot/OxyPlot/OxyPlot.csproj Sat Jun 08 16:53:22 2013 +0000
108.3 @@ -0,0 +1,237 @@
108.4 +<?xml version="1.0" encoding="utf-8"?>
108.5 +<Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
108.6 + <Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
108.7 + <PropertyGroup>
108.8 + <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
108.9 + <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
108.10 + <ProjectGuid>{BCC43E58-E473-403E-A84D-63FEDC723040}</ProjectGuid>
108.11 + <OutputType>Library</OutputType>
108.12 + <AppDesignerFolder>Properties</AppDesignerFolder>
108.13 + <RootNamespace>OxyPlot</RootNamespace>
108.14 + <AssemblyName>OxyPlot</AssemblyName>
108.15 + <TargetFrameworkVersion>v4.0</TargetFrameworkVersion>
108.16 + <FileAlignment>512</FileAlignment>
108.17 + <TargetFrameworkProfile>Client</TargetFrameworkProfile>
108.18 + </PropertyGroup>
108.19 + <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
108.20 + <DebugSymbols>true</DebugSymbols>
108.21 + <DebugType>full</DebugType>
108.22 + <Optimize>false</Optimize>
108.23 + <OutputPath>bin\Debug\</OutputPath>
108.24 + <DefineConstants>DEBUG;TRACE</DefineConstants>
108.25 + <ErrorReport>prompt</ErrorReport>
108.26 + <WarningLevel>4</WarningLevel>
108.27 + </PropertyGroup>
108.28 + <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
108.29 + <DebugType>pdbonly</DebugType>
108.30 + <Optimize>true</Optimize>
108.31 + <OutputPath>..\..\Output\NET40x\</OutputPath>
108.32 + <DefineConstants>TRACE</DefineConstants>
108.33 + <ErrorReport>prompt</ErrorReport>
108.34 + <WarningLevel>4</WarningLevel>
108.35 + <DocumentationFile>..\..\Output\NET40x\OxyPlot.XML</DocumentationFile>
108.36 + </PropertyGroup>
108.37 + <PropertyGroup>
108.38 + <SignAssembly>true</SignAssembly>
108.39 + </PropertyGroup>
108.40 + <PropertyGroup>
108.41 + <AssemblyOriginatorKeyFile>OxyPlot.snk</AssemblyOriginatorKeyFile>
108.42 + </PropertyGroup>
108.43 + <ItemGroup>
108.44 + <Reference Include="System" />
108.45 + <Reference Include="System.Core" />
108.46 + <Reference Include="System.Xml.Linq" />
108.47 + <Reference Include="System.Data.DataSetExtensions" />
108.48 + <Reference Include="Microsoft.CSharp" />
108.49 + <Reference Include="System.Data" />
108.50 + <Reference Include="System.Xml" />
108.51 + </ItemGroup>
108.52 + <ItemGroup>
108.53 + <Compile Include="..\GlobalAssemblyInfo.cs">
108.54 + <Link>Properties\GlobalAssemblyInfo.cs</Link>
108.55 + </Compile>
108.56 + <Compile Include="Annotations\Annotation.cs" />
108.57 + <Compile Include="Annotations\AnnotationLayer.cs" />
108.58 + <Compile Include="Annotations\ArrowAnnotation.cs" />
108.59 + <Compile Include="Annotations\EllipseAnnotation.cs" />
108.60 + <Compile Include="Annotations\ImageAnnotation.cs" />
108.61 + <Compile Include="Annotations\TileMapAnnotation.cs" />
108.62 + <Compile Include="Foundation\PlotLength.cs" />
108.63 + <Compile Include="Foundation\PlotLengthUnit.cs" />
108.64 + <Compile Include="Annotations\RectangleAnnotation.cs" />
108.65 + <Compile Include="Annotations\TextAnnotation.cs" />
108.66 + <Compile Include="Annotations\PolygonAnnotation.cs" />
108.67 + <Compile Include="Annotations\LineAnnotation.cs" />
108.68 + <Compile Include="Annotations\LineAnnotationType.cs" />
108.69 + <Compile Include="Annotations\TextualAnnotation.cs" />
108.70 + <Compile Include="Axes\AngleAxis.cs" />
108.71 + <Compile Include="Axes\Axis.cs" />
108.72 + <Compile Include="Axes\AxisChangedEventArgs.cs" />
108.73 + <Compile Include="Axes\AxisChangeTypes.cs" />
108.74 + <Compile Include="Axes\AxisLayer.cs" />
108.75 + <Compile Include="Axes\AxisPosition.cs" />
108.76 + <Compile Include="Axes\CategoryAxis.cs" />
108.77 + <Compile Include="Axes\ColorAxis.cs" />
108.78 + <Compile Include="Axes\DateTimeAxis.cs" />
108.79 + <Compile Include="Axes\DateTimeIntervalType.cs" />
108.80 + <Compile Include="Axes\LinearAxis.cs" />
108.81 + <Compile Include="Axes\MagnitudeAxis.cs" />
108.82 + <Compile Include="Axes\TickStyle.cs" />
108.83 + <Compile Include="Axes\TimeSpanAxis.cs" />
108.84 + <Compile Include="Foundation\CodeGenerator\CodeGenerationAttribute.cs" />
108.85 + <Compile Include="Foundation\CodeGenerator\CodeGenerator.cs" />
108.86 + <Compile Include="Foundation\CodeGenerator\CodeGeneratorStringExtensions.cs" />
108.87 + <Compile Include="Foundation\CodeGenerator\ICodeGenerating.cs" />
108.88 + <Compile Include="Foundation\ListFiller.cs" />
108.89 + <Compile Include="Foundation\OxyPalette.cs" />
108.90 + <Compile Include="Foundation\OxyPalettes.cs" />
108.91 + <Compile Include="Foundation\PngEncoder.cs" />
108.92 + <Compile Include="Foundation\ScreenVector.cs" />
108.93 + <Compile Include="Foundation\StreamExtensions.cs" />
108.94 + <Compile Include="Foundation\StringHelper.cs" />
108.95 + <Compile Include="Foundation\DoubleExtensions.cs" />
108.96 + <Compile Include="Foundation\FractionHelper.cs" />
108.97 + <Compile Include="Foundation\ArrayHelper.cs" />
108.98 + <Compile Include="Foundation\IDataPoint.cs" />
108.99 + <Compile Include="Foundation\ReflectionHelper.cs" />
108.100 + <Compile Include="Foundation\ScreenPointHelper.cs" />
108.101 + <Compile Include="Manipulators\ZoomManipulator.cs" />
108.102 + <Compile Include="Manipulators\ZoomStepManipulator.cs" />
108.103 + <Compile Include="Manipulators\ResetManipulator.cs" />
108.104 + <Compile Include="Manipulators\ManipulationEventArgs.cs" />
108.105 + <Compile Include="Manipulators\TrackerManipulator.cs" />
108.106 + <Compile Include="Manipulators\ZoomRectangleManipulator.cs" />
108.107 + <Compile Include="Manipulators\ManipulatorBase.cs" />
108.108 + <Compile Include="Manipulators\CursorType.cs" />
108.109 + <Compile Include="Manipulators\PanManipulator.cs" />
108.110 + <Compile Include="Manipulators\TrackerHitResult.cs" />
108.111 + <Compile Include="LibraryDoc.cs" />
108.112 + <Compile Include="NamespaceDoc.cs" />
108.113 + <Compile Include="PlotModel\HitTestResult.cs" />
108.114 + <Compile Include="Foundation\OxyImage.cs" />
108.115 + <Compile Include="Reporting\NamespaceDoc.cs" />
108.116 + <Compile Include="Series\BarSeries\BarItem.cs" />
108.117 + <Compile Include="Series\BarSeries\BarItemBase.cs" />
108.118 + <Compile Include="Series\BarSeries\BarSeriesBase{T}.cs" />
108.119 + <Compile Include="Series\BarSeries\CategorizedItem.cs" />
108.120 + <Compile Include="Series\BarSeries\CategorizedSeries.cs" />
108.121 + <Compile Include="Series\BarSeries\ErrorColumnItem.cs" />
108.122 + <Compile Include="Series\BarSeries\ColumnItem.cs" />
108.123 + <Compile Include="Series\BarSeries\ErrorColumnSeries.cs" />
108.124 + <Compile Include="Series\BarSeries\IStackableSeries.cs" />
108.125 + <Compile Include="Series\BoxPlotItem.cs" />
108.126 + <Compile Include="Series\BoxPlotSeries.cs" />
108.127 + <Compile Include="Foundation\IDataPointProvider.cs" />
108.128 + <Compile Include="Series\HeatMapSeries.cs" />
108.129 + <Compile Include="Series\LineLegendPosition.cs" />
108.130 + <Compile Include="Svg\SvgExporter.cs" />
108.131 + <Compile Include="PlotModel\PlotModel.MouseEvents.cs" />
108.132 + <Compile Include="PlotModel\OxyMouseButton.cs" />
108.133 + <Compile Include="PlotModel\OxyMouseEventArgs.cs" />
108.134 + <Compile Include="PlotModel\PlotElement.cs" />
108.135 + <Compile Include="PlotModel\PlotModel.Legends.cs" />
108.136 + <Compile Include="Foundation\CanonicalSplineHelper.cs" />
108.137 + <Compile Include="Foundation\FontWeights.cs" />
108.138 + <Compile Include="Foundation\OxyThickness.cs" />
108.139 + <Compile Include="Foundation\ScreenPoint.cs" />
108.140 + <Compile Include="Foundation\OxyRect.cs" />
108.141 + <Compile Include="Foundation\OxySize.cs" />
108.142 + <Compile Include="Foundation\SutherlandHodgmanClipping.cs" />
108.143 + <Compile Include="Manipulators\IPlotControl.cs" />
108.144 + <Compile Include="PlotModel\PlotModel.Rendering.cs" />
108.145 + <Compile Include="PlotModel\SelectablePlotElement.cs" />
108.146 + <Compile Include="PlotModel\UIPlotElement.cs" />
108.147 + <Compile Include="Render\AxisRendererBase.cs" />
108.148 + <Compile Include="Foundation\CohenSutherlandClipping.cs" />
108.149 + <Compile Include="Render\AngleAxisRenderer.cs" />
108.150 + <Compile Include="Foundation\HorizontalAlignment.cs" />
108.151 + <Compile Include="Render\MagnitudeAxisRenderer.cs" />
108.152 + <Compile Include="Render\MathRenderingExtensions.cs" />
108.153 + <Compile Include="Foundation\OxyPenLineJoin.cs" />
108.154 + <Compile Include="Render\RenderContextBase.cs" />
108.155 + <Compile Include="Render\RenderingExtensions.cs" />
108.156 + <Compile Include="Render\HorizontalAndVerticalAxisRenderer.cs" />
108.157 + <Compile Include="Render\IRenderContext.cs" />
108.158 + <Compile Include="Foundation\VerticalAlignment.cs" />
108.159 + <Compile Include="Reporting\ReportWriters\WikiReportWriter.cs" />
108.160 + <Compile Include="Reporting\ReportWriters\HtmlReportWriter.cs" />
108.161 + <Compile Include="Reporting\ReportWriters\IReportWriter.cs" />
108.162 + <Compile Include="Reporting\ReportWriters\StringExtensions.cs" />
108.163 + <Compile Include="Reporting\ReportWriters\TextReportWriter.cs" />
108.164 + <Compile Include="Reporting\Report\ItemsTable.cs" />
108.165 + <Compile Include="Reporting\Report\ParagraphStyle.cs" />
108.166 + <Compile Include="Reporting\Report\ReportStyle.cs" />
108.167 + <Compile Include="Reporting\Report\TableOfContents.cs" />
108.168 + <Compile Include="Reporting\Report\DrawingFigure.cs" />
108.169 + <Compile Include="Reporting\Report\Equation.cs" />
108.170 + <Compile Include="Reporting\Report\Figure.cs" />
108.171 + <Compile Include="Reporting\Report\Header.cs" />
108.172 + <Compile Include="Reporting\Report\HeaderHelper.cs" />
108.173 + <Compile Include="Reporting\Report\Image.cs" />
108.174 + <Compile Include="Reporting\Report\Paragraph.cs" />
108.175 + <Compile Include="Reporting\Report\PlotFigure.cs" />
108.176 + <Compile Include="Reporting\Report\PropertyTable.cs" />
108.177 + <Compile Include="Reporting\Report\Report.cs" />
108.178 + <Compile Include="Reporting\Report\ReportItem.cs" />
108.179 + <Compile Include="Reporting\Report\ReportSection.cs" />
108.180 + <Compile Include="Reporting\Report\Table.cs" />
108.181 + <Compile Include="Reporting\Report\ItemsTableField.cs" />
108.182 + <Compile Include="Series\AreaSeries.cs" />
108.183 + <Compile Include="Foundation\OxyPen.cs" />
108.184 + <Compile Include="Foundation\LineStyleHelper.cs" />
108.185 + <Compile Include="Foundation\DataPoint.cs" />
108.186 + <Compile Include="Series\BarSeries\LabelPlacement.cs" />
108.187 + <Compile Include="Series\CandleStickSeries.cs" />
108.188 + <Compile Include="Foundation\Conrec.cs" />
108.189 + <Compile Include="Series\ContourSeries.cs" />
108.190 + <Compile Include="Series\BarSeries\ColumnSeries.cs" />
108.191 + <Compile Include="Series\BarSeries\BarSeries.cs" />
108.192 + <Compile Include="Series\BarSeries\BarSeriesBase.cs" />
108.193 + <Compile Include="Series\BarSeries\IntervalBarItem.cs" />
108.194 + <Compile Include="Series\BarSeries\RectangleBarItem.cs" />
108.195 + <Compile Include="Series\BarSeries\RectangleBarSeries.cs" />
108.196 + <Compile Include="Series\BarSeries\IntervalBarSeries.cs" />
108.197 + <Compile Include="Series\BarSeries\TornadoBarItem.cs" />
108.198 + <Compile Include="Series\BarSeries\TornadoBarSeries.cs" />
108.199 + <Compile Include="Series\ItemsSeries.cs" />
108.200 + <Compile Include="Series\DataPointSeries.cs" />
108.201 + <Compile Include="Series\HighLowItem.cs" />
108.202 + <Compile Include="Series\HighLowSeries.cs" />
108.203 + <Compile Include="Series\ScatterPoint.cs" />
108.204 + <Compile Include="Series\Series.cs" />
108.205 + <Compile Include="Series\StemSeries.cs" />
108.206 + <Compile Include="Series\StairStepSeries.cs" />
108.207 + <Compile Include="Series\ITrackableSeries.cs" />
108.208 + <Compile Include="Series\ScatterSeries.cs" />
108.209 + <Compile Include="Series\TwoColorLineSeries.cs" />
108.210 + <Compile Include="Series\XYAxisSeries.cs" />
108.211 + <Compile Include="Series\PieSeries.cs" />
108.212 + <Compile Include="Series\FunctionSeries.cs" />
108.213 + <Compile Include="Series\PieSlice.cs" />
108.214 + <Compile Include="Svg\SvgRenderContext.cs" />
108.215 + <Compile Include="Svg\SvgWriter.cs" />
108.216 + <Compile Include="Foundation\OxyColor.cs" />
108.217 + <Compile Include="Foundation\OxyColors.cs" />
108.218 + <Compile Include="Series\LineSeries.cs" />
108.219 + <Compile Include="Foundation\LineStyle.cs" />
108.220 + <Compile Include="Axes\LogarithmicAxis.cs" />
108.221 + <Compile Include="Foundation\MarkerType.cs" />
108.222 + <Compile Include="PlotModel\PlotModel.cs" />
108.223 + <Compile Include="Properties\AssemblyInfo.cs" />
108.224 + <Compile Include="Foundation\XmlWriterBase.cs" />
108.225 + </ItemGroup>
108.226 + <ItemGroup>
108.227 + <None Include="ClassDiagrams\Series.cd" />
108.228 + <None Include="ClassDiagrams\PlotModel.cd" />
108.229 + <None Include="ClassDiagrams\Reporting.cd" />
108.230 + <None Include="OxyPlot.snk" />
108.231 + </ItemGroup>
108.232 + <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
108.233 + <!-- To modify your build process, add your task inside one of the targets below and uncomment it.
108.234 + Other similar extension points exist, see Microsoft.Common.targets.
108.235 + <Target Name="BeforeBuild">
108.236 + </Target>
108.237 + <Target Name="AfterBuild">
108.238 + </Target>
108.239 + -->
108.240 +</Project>
108.241 \ No newline at end of file
109.1 Binary file External/OxyPlot/OxyPlot/OxyPlot.snk has changed
110.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
110.2 +++ b/External/OxyPlot/OxyPlot/PlotModel/HitTestResult.cs Sat Jun 08 16:53:22 2013 +0000
110.3 @@ -0,0 +1,79 @@
110.4 +// --------------------------------------------------------------------------------------------------------------------
110.5 +// <copyright file="HitTestResult.cs" company="OxyPlot">
110.6 +// The MIT License (MIT)
110.7 +//
110.8 +// Copyright (c) 2012 Oystein Bjorke
110.9 +//
110.10 +// Permission is hereby granted, free of charge, to any person obtaining a
110.11 +// copy of this software and associated documentation files (the
110.12 +// "Software"), to deal in the Software without restriction, including
110.13 +// without limitation the rights to use, copy, modify, merge, publish,
110.14 +// distribute, sublicense, and/or sell copies of the Software, and to
110.15 +// permit persons to whom the Software is furnished to do so, subject to
110.16 +// the following conditions:
110.17 +//
110.18 +// The above copyright notice and this permission notice shall be included
110.19 +// in all copies or substantial portions of the Software.
110.20 +//
110.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
110.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
110.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
110.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
110.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
110.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
110.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
110.28 +// </copyright>
110.29 +// <summary>
110.30 +// Represents a hit test result.
110.31 +// </summary>
110.32 +// --------------------------------------------------------------------------------------------------------------------
110.33 +namespace OxyPlot
110.34 +{
110.35 + /// <summary>
110.36 + /// Represents a hit test result.
110.37 + /// </summary>
110.38 + public class HitTestResult
110.39 + {
110.40 + /// <summary>
110.41 + /// Initializes a new instance of the <see cref="HitTestResult"/> class.
110.42 + /// </summary>
110.43 + public HitTestResult()
110.44 + {
110.45 + }
110.46 +
110.47 + /// <summary>
110.48 + /// Initializes a new instance of the <see cref="HitTestResult"/> class.
110.49 + /// </summary>
110.50 + /// <param name="nhp">The nearest hit point.</param>
110.51 + /// <param name="item">The item.</param>
110.52 + /// <param name="index">The index.</param>
110.53 + public HitTestResult(ScreenPoint nhp, object item = null, double index = 0)
110.54 + {
110.55 + this.NearestHitPoint = nhp;
110.56 + this.Item = item;
110.57 + this.Index = index;
110.58 + }
110.59 +
110.60 + /// <summary>
110.61 + /// Gets or sets the index of the hit (if available).
110.62 + /// </summary>
110.63 + /// <value> The index. </value>
110.64 + /// <remarks>
110.65 + /// If the hit was in the middle between point 1 and 2, index = 1.5.
110.66 + /// </remarks>
110.67 + public double Index { get; set; }
110.68 +
110.69 + /// <summary>
110.70 + /// Gets or sets the item of the hit.
110.71 + /// </summary>
110.72 + /// <value> The item. </value>
110.73 + public object Item { get; set; }
110.74 +
110.75 + /// <summary>
110.76 + /// Gets or sets the position of the nearest hit point.
110.77 + /// </summary>
110.78 + /// <value> The nearest hit point. </value>
110.79 + public ScreenPoint NearestHitPoint { get; set; }
110.80 +
110.81 + }
110.82 +}
110.83 \ No newline at end of file
111.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
111.2 +++ b/External/OxyPlot/OxyPlot/PlotModel/OxyMouseButton.cs Sat Jun 08 16:53:22 2013 +0000
111.3 @@ -0,0 +1,67 @@
111.4 +// --------------------------------------------------------------------------------------------------------------------
111.5 +// <copyright file="OxyMouseButton.cs" company="OxyPlot">
111.6 +// The MIT License (MIT)
111.7 +//
111.8 +// Copyright (c) 2012 Oystein Bjorke
111.9 +//
111.10 +// Permission is hereby granted, free of charge, to any person obtaining a
111.11 +// copy of this software and associated documentation files (the
111.12 +// "Software"), to deal in the Software without restriction, including
111.13 +// without limitation the rights to use, copy, modify, merge, publish,
111.14 +// distribute, sublicense, and/or sell copies of the Software, and to
111.15 +// permit persons to whom the Software is furnished to do so, subject to
111.16 +// the following conditions:
111.17 +//
111.18 +// The above copyright notice and this permission notice shall be included
111.19 +// in all copies or substantial portions of the Software.
111.20 +//
111.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
111.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
111.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
111.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
111.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
111.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
111.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
111.28 +// </copyright>
111.29 +// <summary>
111.30 +// The mouse buttons.
111.31 +// </summary>
111.32 +// --------------------------------------------------------------------------------------------------------------------
111.33 +namespace OxyPlot
111.34 +{
111.35 + /// <summary>
111.36 + /// Specifies constants that define which mouse button was pressed.
111.37 + /// </summary>
111.38 + public enum OxyMouseButton
111.39 + {
111.40 + /// <summary>
111.41 + /// No mouse button.
111.42 + /// </summary>
111.43 + None = 0,
111.44 +
111.45 + /// <summary>
111.46 + /// The left mouse button.
111.47 + /// </summary>
111.48 + Left = 1,
111.49 +
111.50 + /// <summary>
111.51 + /// The middle mouse button.
111.52 + /// </summary>
111.53 + Middle = 2,
111.54 +
111.55 + /// <summary>
111.56 + /// The right mouse button.
111.57 + /// </summary>
111.58 + Right = 3,
111.59 +
111.60 + /// <summary>
111.61 + /// The first extended mouse button.
111.62 + /// </summary>
111.63 + XButton1 = 4,
111.64 +
111.65 + /// <summary>
111.66 + /// The second extended mouse button.
111.67 + /// </summary>
111.68 + XButton2 = 5,
111.69 + }
111.70 +}
111.71 \ No newline at end of file
112.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
112.2 +++ b/External/OxyPlot/OxyPlot/PlotModel/OxyMouseEventArgs.cs Sat Jun 08 16:53:22 2013 +0000
112.3 @@ -0,0 +1,87 @@
112.4 +// --------------------------------------------------------------------------------------------------------------------
112.5 +// <copyright file="OxyMouseEventArgs.cs" company="OxyPlot">
112.6 +// The MIT License (MIT)
112.7 +//
112.8 +// Copyright (c) 2012 Oystein Bjorke
112.9 +//
112.10 +// Permission is hereby granted, free of charge, to any person obtaining a
112.11 +// copy of this software and associated documentation files (the
112.12 +// "Software"), to deal in the Software without restriction, including
112.13 +// without limitation the rights to use, copy, modify, merge, publish,
112.14 +// distribute, sublicense, and/or sell copies of the Software, and to
112.15 +// permit persons to whom the Software is furnished to do so, subject to
112.16 +// the following conditions:
112.17 +//
112.18 +// The above copyright notice and this permission notice shall be included
112.19 +// in all copies or substantial portions of the Software.
112.20 +//
112.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
112.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
112.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
112.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
112.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
112.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
112.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
112.28 +// </copyright>
112.29 +// <summary>
112.30 +// Represents event arguments for 3D mouse events events.
112.31 +// </summary>
112.32 +// --------------------------------------------------------------------------------------------------------------------
112.33 +namespace OxyPlot
112.34 +{
112.35 + using System;
112.36 +
112.37 + /// <summary>
112.38 + /// Provides data for the mouse events.
112.39 + /// </summary>
112.40 + public class OxyMouseEventArgs : EventArgs
112.41 + {
112.42 + /// <summary>
112.43 + /// Gets or sets the mouse button that has changed.
112.44 + /// </summary>
112.45 + public OxyMouseButton ChangedButton { get; set; }
112.46 +
112.47 + /// <summary>
112.48 + /// Gets or sets the click count.
112.49 + /// </summary>
112.50 + /// <value> The click count. </value>
112.51 + public int ClickCount { get; set; }
112.52 +
112.53 + /// <summary>
112.54 + /// Gets or sets a value indicating whether Handled.
112.55 + /// </summary>
112.56 + public bool Handled { get; set; }
112.57 +
112.58 + /// <summary>
112.59 + /// Gets or sets a value indicating whether the alt key was pressed when the event was raised.
112.60 + /// </summary>
112.61 + public bool IsAltDown { get; set; }
112.62 +
112.63 + /// <summary>
112.64 + /// Gets or sets a value indicating whether the control key was pressed when the event was raised.
112.65 + /// </summary>
112.66 + public bool IsControlDown { get; set; }
112.67 +
112.68 + /// <summary>
112.69 + /// Gets or sets a value indicating whether the shift key was pressed when the event was raised.
112.70 + /// </summary>
112.71 + public bool IsShiftDown { get; set; }
112.72 +
112.73 + /// <summary>
112.74 + /// Gets or sets the hit test result.
112.75 + /// </summary>
112.76 + public HitTestResult HitTestResult { get; set; }
112.77 +
112.78 + /// <summary>
112.79 + /// Gets or sets the plot control.
112.80 + /// </summary>
112.81 + /// <value> The plot control. </value>
112.82 + public IPlotControl PlotControl { get; set; }
112.83 +
112.84 + /// <summary>
112.85 + /// Gets or sets the position.
112.86 + /// </summary>
112.87 + public ScreenPoint Position { get; set; }
112.88 +
112.89 + }
112.90 +}
112.91 \ No newline at end of file
113.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
113.2 +++ b/External/OxyPlot/OxyPlot/PlotModel/PlotElement.cs Sat Jun 08 16:53:22 2013 +0000
113.3 @@ -0,0 +1,142 @@
113.4 +// --------------------------------------------------------------------------------------------------------------------
113.5 +// <copyright file="PlotElement.cs" company="OxyPlot">
113.6 +// The MIT License (MIT)
113.7 +//
113.8 +// Copyright (c) 2012 Oystein Bjorke
113.9 +//
113.10 +// Permission is hereby granted, free of charge, to any person obtaining a
113.11 +// copy of this software and associated documentation files (the
113.12 +// "Software"), to deal in the Software without restriction, including
113.13 +// without limitation the rights to use, copy, modify, merge, publish,
113.14 +// distribute, sublicense, and/or sell copies of the Software, and to
113.15 +// permit persons to whom the Software is furnished to do so, subject to
113.16 +// the following conditions:
113.17 +//
113.18 +// The above copyright notice and this permission notice shall be included
113.19 +// in all copies or substantial portions of the Software.
113.20 +//
113.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
113.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
113.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
113.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
113.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
113.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
113.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
113.28 +// </copyright>
113.29 +// <summary>
113.30 +// Abstract base class for all plottable elements (Axes, Annotations, Series).
113.31 +// </summary>
113.32 +// --------------------------------------------------------------------------------------------------------------------
113.33 +namespace OxyPlot
113.34 +{
113.35 + using System;
113.36 +
113.37 + /// <summary>
113.38 + /// Provides an abstract base class for elements contained in a <see cref="PlotModel"/>.
113.39 + /// </summary>
113.40 + public abstract class PlotElement
113.41 + {
113.42 + /// <summary>
113.43 + /// Initializes a new instance of the <see cref="PlotElement"/> class.
113.44 + /// </summary>
113.45 + protected PlotElement()
113.46 + {
113.47 + this.Font = null;
113.48 + this.FontSize = double.NaN;
113.49 + this.FontWeight = FontWeights.Normal;
113.50 + }
113.51 +
113.52 + /// <summary>
113.53 + /// Gets or sets the font.
113.54 + /// </summary>
113.55 + /// <value> The font. </value>
113.56 + /// <remarks>
113.57 + /// If the value is null, the parent PlotModel's DefaultFont will be used.
113.58 + /// </remarks>
113.59 + public string Font { get; set; }
113.60 +
113.61 + /// <summary>
113.62 + /// Gets or sets the size of the font.
113.63 + /// </summary>
113.64 + /// <value> The size of the font. </value>
113.65 + /// <remarks>
113.66 + /// If the value is NaN, the parent PlotModel's DefaultFontSize will be used.
113.67 + /// </remarks>
113.68 + public double FontSize { get; set; }
113.69 +
113.70 + /// <summary>
113.71 + /// Gets or sets the font weight.
113.72 + /// </summary>
113.73 + /// <value> The font weight. </value>
113.74 + public double FontWeight { get; set; }
113.75 +
113.76 + /// <summary>
113.77 + /// Gets the parent plot model.
113.78 + /// </summary>
113.79 + public PlotModel PlotModel { get; internal set; }
113.80 +
113.81 + /// <summary>
113.82 + /// Gets or sets an arbitrary object value that can be used to store custom information about this plot element.
113.83 + /// </summary>
113.84 + /// <value> The intended value. This property has no default value. </value>
113.85 + /// <remarks>
113.86 + /// This property is analogous to Tag properties in other Microsoft programming models. Tag is intended to provide a pre-existing property location where you can store some basic custom information about any PlotElement without requiring you to subclass an element.
113.87 + /// </remarks>
113.88 + public object Tag { get; set; }
113.89 +
113.90 + /// <summary>
113.91 + /// Gets or sets the color of the text.
113.92 + /// </summary>
113.93 + /// <value> The color of the text. </value>
113.94 + /// <remarks>
113.95 + /// If the value is null, the TextColor of the parent PlotModel will be used.
113.96 + /// </remarks>
113.97 + public OxyColor TextColor { get; set; }
113.98 +
113.99 + /// <summary>
113.100 + /// Gets the actual font.
113.101 + /// </summary>
113.102 + protected internal string ActualFont
113.103 + {
113.104 + get
113.105 + {
113.106 + return this.Font ?? this.PlotModel.DefaultFont;
113.107 + }
113.108 + }
113.109 +
113.110 + /// <summary>
113.111 + /// Gets the actual size of the font.
113.112 + /// </summary>
113.113 + /// <value> The actual size of the font. </value>
113.114 + protected internal double ActualFontSize
113.115 + {
113.116 + get
113.117 + {
113.118 + return !double.IsNaN(this.FontSize) ? this.FontSize : this.PlotModel.DefaultFontSize;
113.119 + }
113.120 + }
113.121 +
113.122 + /// <summary>
113.123 + /// Gets the actual font weight.
113.124 + /// </summary>
113.125 + protected internal double ActualFontWeight
113.126 + {
113.127 + get
113.128 + {
113.129 + return this.FontWeight;
113.130 + }
113.131 + }
113.132 +
113.133 + /// <summary>
113.134 + /// Gets the actual color of the text.
113.135 + /// </summary>
113.136 + /// <value> The actual color of the text. </value>
113.137 + protected internal OxyColor ActualTextColor
113.138 + {
113.139 + get
113.140 + {
113.141 + return this.TextColor ?? this.PlotModel.TextColor;
113.142 + }
113.143 + }
113.144 + }
113.145 +}
113.146 \ No newline at end of file
114.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
114.2 +++ b/External/OxyPlot/OxyPlot/PlotModel/PlotModel.Legends.cs Sat Jun 08 16:53:22 2013 +0000
114.3 @@ -0,0 +1,507 @@
114.4 +// --------------------------------------------------------------------------------------------------------------------
114.5 +// <copyright file="PlotModel.Legends.cs" company="OxyPlot">
114.6 +// The MIT License (MIT)
114.7 +//
114.8 +// Copyright (c) 2012 Oystein Bjorke
114.9 +//
114.10 +// Permission is hereby granted, free of charge, to any person obtaining a
114.11 +// copy of this software and associated documentation files (the
114.12 +// "Software"), to deal in the Software without restriction, including
114.13 +// without limitation the rights to use, copy, modify, merge, publish,
114.14 +// distribute, sublicense, and/or sell copies of the Software, and to
114.15 +// permit persons to whom the Software is furnished to do so, subject to
114.16 +// the following conditions:
114.17 +//
114.18 +// The above copyright notice and this permission notice shall be included
114.19 +// in all copies or substantial portions of the Software.
114.20 +//
114.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
114.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
114.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
114.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
114.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
114.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
114.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
114.28 +// </copyright>
114.29 +// <summary>
114.30 +// Partial PlotModel class - this file contains methods related to the series legends.
114.31 +// </summary>
114.32 +// --------------------------------------------------------------------------------------------------------------------
114.33 +namespace OxyPlot
114.34 +{
114.35 + using System;
114.36 + using System.Collections.Generic;
114.37 + using System.Linq;
114.38 +
114.39 + using OxyPlot.Series;
114.40 +
114.41 + public partial class PlotModel
114.42 + {
114.43 + /// <summary>
114.44 + /// Makes the LegendOrientation property safe.
114.45 + /// </summary>
114.46 + /// <remarks>
114.47 + /// If Legend is positioned left or right, force it to vertical orientation
114.48 + /// </remarks>
114.49 + private void EnsureLegendProperties()
114.50 + {
114.51 + switch (this.LegendPosition)
114.52 + {
114.53 + case LegendPosition.LeftTop:
114.54 + case LegendPosition.LeftMiddle:
114.55 + case LegendPosition.LeftBottom:
114.56 + case LegendPosition.RightTop:
114.57 + case LegendPosition.RightMiddle:
114.58 + case LegendPosition.RightBottom:
114.59 + if (this.LegendOrientation == LegendOrientation.Horizontal)
114.60 + {
114.61 + this.LegendOrientation = LegendOrientation.Vertical;
114.62 + }
114.63 +
114.64 + break;
114.65 + }
114.66 + }
114.67 +
114.68 + /// <summary>
114.69 + /// Gets the rectangle of the legend box.
114.70 + /// </summary>
114.71 + /// <param name="legendSize">Size of the legend box.</param>
114.72 + /// <returns>A rectangle.</returns>
114.73 + private OxyRect GetLegendRectangle(OxySize legendSize)
114.74 + {
114.75 + double top = 0;
114.76 + double left = 0;
114.77 + if (this.LegendPlacement == LegendPlacement.Outside)
114.78 + {
114.79 + switch (this.LegendPosition)
114.80 + {
114.81 + case LegendPosition.LeftTop:
114.82 + case LegendPosition.LeftMiddle:
114.83 + case LegendPosition.LeftBottom:
114.84 + left = this.PlotAndAxisArea.Left - legendSize.Width - this.LegendMargin;
114.85 + break;
114.86 + case LegendPosition.RightTop:
114.87 + case LegendPosition.RightMiddle:
114.88 + case LegendPosition.RightBottom:
114.89 + left = this.PlotAndAxisArea.Right + this.LegendMargin;
114.90 + break;
114.91 + case LegendPosition.TopLeft:
114.92 + case LegendPosition.TopCenter:
114.93 + case LegendPosition.TopRight:
114.94 + top = this.PlotAndAxisArea.Top - legendSize.Height - this.LegendMargin;
114.95 + break;
114.96 + case LegendPosition.BottomLeft:
114.97 + case LegendPosition.BottomCenter:
114.98 + case LegendPosition.BottomRight:
114.99 + top = this.PlotAndAxisArea.Bottom + this.LegendMargin;
114.100 + break;
114.101 + }
114.102 +
114.103 + switch (this.LegendPosition)
114.104 + {
114.105 + case LegendPosition.TopLeft:
114.106 + case LegendPosition.BottomLeft:
114.107 + left = this.PlotArea.Left;
114.108 + break;
114.109 + case LegendPosition.TopRight:
114.110 + case LegendPosition.BottomRight:
114.111 + left = this.PlotArea.Right - legendSize.Width;
114.112 + break;
114.113 + case LegendPosition.LeftTop:
114.114 + case LegendPosition.RightTop:
114.115 + top = this.PlotArea.Top;
114.116 + break;
114.117 + case LegendPosition.LeftBottom:
114.118 + case LegendPosition.RightBottom:
114.119 + top = this.PlotArea.Bottom - legendSize.Height;
114.120 + break;
114.121 + case LegendPosition.LeftMiddle:
114.122 + case LegendPosition.RightMiddle:
114.123 + top = (this.PlotArea.Top + this.PlotArea.Bottom - legendSize.Height) * 0.5;
114.124 + break;
114.125 + case LegendPosition.TopCenter:
114.126 + case LegendPosition.BottomCenter:
114.127 + left = (this.PlotArea.Left + this.PlotArea.Right - legendSize.Width) * 0.5;
114.128 + break;
114.129 + }
114.130 + }
114.131 + else
114.132 + {
114.133 + switch (this.LegendPosition)
114.134 + {
114.135 + case LegendPosition.LeftTop:
114.136 + case LegendPosition.LeftMiddle:
114.137 + case LegendPosition.LeftBottom:
114.138 + left = this.PlotArea.Left + this.LegendMargin;
114.139 + break;
114.140 + case LegendPosition.RightTop:
114.141 + case LegendPosition.RightMiddle:
114.142 + case LegendPosition.RightBottom:
114.143 + left = this.PlotArea.Right - legendSize.Width - this.LegendMargin;
114.144 + break;
114.145 + case LegendPosition.TopLeft:
114.146 + case LegendPosition.TopCenter:
114.147 + case LegendPosition.TopRight:
114.148 + top = this.PlotArea.Top + this.LegendMargin;
114.149 + break;
114.150 + case LegendPosition.BottomLeft:
114.151 + case LegendPosition.BottomCenter:
114.152 + case LegendPosition.BottomRight:
114.153 + top = this.PlotArea.Bottom - legendSize.Height - this.LegendMargin;
114.154 + break;
114.155 + }
114.156 +
114.157 + switch (this.LegendPosition)
114.158 + {
114.159 + case LegendPosition.TopLeft:
114.160 + case LegendPosition.BottomLeft:
114.161 + left = this.PlotArea.Left + this.LegendMargin;
114.162 + break;
114.163 + case LegendPosition.TopRight:
114.164 + case LegendPosition.BottomRight:
114.165 + left = this.PlotArea.Right - legendSize.Width - this.LegendMargin;
114.166 + break;
114.167 + case LegendPosition.LeftTop:
114.168 + case LegendPosition.RightTop:
114.169 + top = this.PlotArea.Top + this.LegendMargin;
114.170 + break;
114.171 + case LegendPosition.LeftBottom:
114.172 + case LegendPosition.RightBottom:
114.173 + top = this.PlotArea.Bottom - legendSize.Height - this.LegendMargin;
114.174 + break;
114.175 +
114.176 + case LegendPosition.LeftMiddle:
114.177 + case LegendPosition.RightMiddle:
114.178 + top = (this.PlotArea.Top + this.PlotArea.Bottom - legendSize.Height) * 0.5;
114.179 + break;
114.180 + case LegendPosition.TopCenter:
114.181 + case LegendPosition.BottomCenter:
114.182 + left = (this.PlotArea.Left + this.PlotArea.Right - legendSize.Width) * 0.5;
114.183 + break;
114.184 + }
114.185 + }
114.186 +
114.187 + return new OxyRect(left, top, legendSize.Width, legendSize.Height);
114.188 + }
114.189 +
114.190 + /// <summary>
114.191 + /// Renders the legend for the specified series.
114.192 + /// </summary>
114.193 + /// <param name="rc">
114.194 + /// The render context.
114.195 + /// </param>
114.196 + /// <param name="s">
114.197 + /// The series.
114.198 + /// </param>
114.199 + /// <param name="rect">
114.200 + /// The position and size of the legend.
114.201 + /// </param>
114.202 + private void RenderLegend(IRenderContext rc, Series.Series s, OxyRect rect)
114.203 + {
114.204 + double x = rect.Left;
114.205 + switch (this.LegendItemAlignment)
114.206 + {
114.207 + case HorizontalAlignment.Center:
114.208 + x = (rect.Left + rect.Right) / 2;
114.209 + if (this.LegendSymbolPlacement == LegendSymbolPlacement.Left)
114.210 + {
114.211 + x -= (this.LegendSymbolLength + this.LegendSymbolMargin) / 2;
114.212 + }
114.213 + else
114.214 + {
114.215 + x -= (this.LegendSymbolLength + this.LegendSymbolMargin) / 2;
114.216 + }
114.217 +
114.218 + break;
114.219 + case HorizontalAlignment.Right:
114.220 + x = rect.Right;
114.221 +
114.222 + // if (LegendSymbolPlacement == LegendSymbolPlacement.Right)
114.223 + x -= this.LegendSymbolLength + this.LegendSymbolMargin;
114.224 + break;
114.225 + }
114.226 +
114.227 + if (this.LegendSymbolPlacement == LegendSymbolPlacement.Left)
114.228 + {
114.229 + x += this.LegendSymbolLength + this.LegendSymbolMargin;
114.230 + }
114.231 +
114.232 + double y = rect.Top;
114.233 + var maxsize = new OxySize(Math.Max(rect.Right - x, 0), Math.Max(rect.Bottom - y, 0));
114.234 +
114.235 + var textSize = rc.DrawMathText(
114.236 + new ScreenPoint(x, y),
114.237 + s.Title,
114.238 + this.LegendTextColor ?? this.TextColor,
114.239 + this.LegendFont ?? this.DefaultFont,
114.240 + this.LegendFontSize,
114.241 + this.LegendFontWeight,
114.242 + 0,
114.243 + this.LegendItemAlignment,
114.244 + VerticalAlignment.Top,
114.245 + maxsize,
114.246 + true);
114.247 + double x0 = x;
114.248 + switch (this.LegendItemAlignment)
114.249 + {
114.250 + case HorizontalAlignment.Center:
114.251 + x0 = x - (textSize.Width * 0.5);
114.252 + break;
114.253 + case HorizontalAlignment.Right:
114.254 + x0 = x - textSize.Width;
114.255 + break;
114.256 + }
114.257 +
114.258 + var symbolRect =
114.259 + new OxyRect(
114.260 + this.LegendSymbolPlacement == LegendSymbolPlacement.Right
114.261 + ? x0 + textSize.Width + this.LegendSymbolMargin
114.262 + : x0 - this.LegendSymbolMargin - this.LegendSymbolLength,
114.263 + rect.Top,
114.264 + this.LegendSymbolLength,
114.265 + textSize.Height);
114.266 +
114.267 + s.RenderLegend(rc, symbolRect);
114.268 + }
114.269 +
114.270 + /// <summary>
114.271 + /// Measures the legends.
114.272 + /// </summary>
114.273 + /// <param name="rc">
114.274 + /// The render context.
114.275 + /// </param>
114.276 + /// <param name="availableSize">
114.277 + /// The available size for the legend box.
114.278 + /// </param>
114.279 + /// <returns>
114.280 + /// The size of the legend box.
114.281 + /// </returns>
114.282 + private OxySize MeasureLegends(IRenderContext rc, OxySize availableSize)
114.283 + {
114.284 + return this.RenderOrMeasureLegends(rc, new OxyRect(0, 0, availableSize.Width, availableSize.Height), true);
114.285 + }
114.286 +
114.287 + /// <summary>
114.288 + /// Renders or measures the legends.
114.289 + /// </summary>
114.290 + /// <param name="rc">
114.291 + /// The render context.
114.292 + /// </param>
114.293 + /// <param name="rect">
114.294 + /// The rectangle.
114.295 + /// </param>
114.296 + private void RenderLegends(IRenderContext rc, OxyRect rect)
114.297 + {
114.298 + this.RenderOrMeasureLegends(rc, rect);
114.299 + }
114.300 +
114.301 + /// <summary>
114.302 + /// Renders or measures the legends.
114.303 + /// </summary>
114.304 + /// <param name="rc">
114.305 + /// The render context.
114.306 + /// </param>
114.307 + /// <param name="rect">
114.308 + /// Provides the available size if measuring, otherwise it provides the position and size of the legend.
114.309 + /// </param>
114.310 + /// <param name="measureOnly">
114.311 + /// Specify if the size of the legend box should be measured only (not rendered).
114.312 + /// </param>
114.313 + /// <returns>
114.314 + /// The size of the legend box.
114.315 + /// </returns>
114.316 + private OxySize RenderOrMeasureLegends(IRenderContext rc, OxyRect rect, bool measureOnly = false)
114.317 + {
114.318 + // Render background and border around legend
114.319 + if (!measureOnly && rect.Width > 0 && rect.Height > 0)
114.320 + {
114.321 + rc.DrawRectangleAsPolygon(rect, this.LegendBackground, this.LegendBorder, this.LegendBorderThickness);
114.322 + }
114.323 +
114.324 + double availableWidth = rect.Width;
114.325 + double availableHeight = rect.Height;
114.326 +
114.327 + double x = this.LegendPadding;
114.328 + double top = this.LegendPadding;
114.329 +
114.330 + var size = new OxySize();
114.331 +
114.332 + // Render/measure the legend title
114.333 + if (!string.IsNullOrEmpty(this.LegendTitle))
114.334 + {
114.335 + OxySize titleSize;
114.336 + if (measureOnly)
114.337 + {
114.338 + titleSize = rc.MeasureMathText(
114.339 + this.LegendTitle,
114.340 + this.LegendTitleFont ?? DefaultFont,
114.341 + this.LegendTitleFontSize,
114.342 + this.LegendTitleFontWeight);
114.343 + }
114.344 + else
114.345 + {
114.346 + titleSize = rc.DrawMathText(
114.347 + new ScreenPoint(rect.Left + x, rect.Top + top),
114.348 + this.LegendTitle,
114.349 + this.LegendTitleColor ?? this.TextColor,
114.350 + this.LegendTitleFont ?? this.DefaultFont,
114.351 + this.LegendTitleFontSize,
114.352 + this.LegendTitleFontWeight,
114.353 + 0,
114.354 + HorizontalAlignment.Left,
114.355 + VerticalAlignment.Top,
114.356 + null,
114.357 + true);
114.358 + }
114.359 +
114.360 + top += titleSize.Height;
114.361 + size.Width = x + titleSize.Width + this.LegendPadding;
114.362 + size.Height = top + titleSize.Height;
114.363 + }
114.364 +
114.365 + double y = top;
114.366 +
114.367 + double lineHeight = 0;
114.368 +
114.369 + // tolerance for floating-point number comparisons
114.370 + const double Epsilon = 1e-3;
114.371 +
114.372 + // the maximum item with in the column being rendered (only used for vertical orientation)
114.373 + double maxItemWidth = 0;
114.374 +
114.375 + var items = this.LegendItemOrder == LegendItemOrder.Reverse ? this.VisibleSeries.Reverse() : this.VisibleSeries;
114.376 +
114.377 + // When orientation is vertical and alignment is center or right, the items cannot be rendered before
114.378 + // the max item width has been calculated. Render the items for each column, and at the end.
114.379 + var seriesToRender = new Dictionary<Series.Series, OxyRect>();
114.380 + Action renderItems = () =>
114.381 + {
114.382 + foreach (var sr in seriesToRender)
114.383 + {
114.384 + var itemRect = sr.Value;
114.385 + var itemSeries = sr.Key;
114.386 +
114.387 + double rwidth = itemRect.Width;
114.388 + if (itemRect.Left + rwidth + this.LegendPadding > rect.Left + availableWidth)
114.389 + {
114.390 + rwidth = rect.Left + availableWidth - itemRect.Left - this.LegendPadding;
114.391 + }
114.392 +
114.393 + double rheight = itemRect.Height;
114.394 + if (rect.Top + rheight + this.LegendPadding > rect.Top + availableHeight)
114.395 + {
114.396 + rheight = rect.Top + availableHeight - rect.Top - this.LegendPadding;
114.397 + }
114.398 +
114.399 + var r = new OxyRect(itemRect.Left, itemRect.Top, Math.Max(rwidth, 0), Math.Max(rheight, 0));
114.400 + this.RenderLegend(rc, itemSeries, r);
114.401 + }
114.402 +
114.403 + seriesToRender.Clear();
114.404 + };
114.405 +
114.406 + foreach (var s in items)
114.407 + {
114.408 + // Skip series with empty title
114.409 + if (string.IsNullOrEmpty(s.Title))
114.410 + {
114.411 + continue;
114.412 + }
114.413 +
114.414 + var textSize = rc.MeasureMathText(s.Title, this.LegendFont ?? DefaultFont, this.LegendFontSize, this.LegendFontWeight);
114.415 + double itemWidth = this.LegendSymbolLength + this.LegendSymbolMargin + textSize.Width;
114.416 + double itemHeight = textSize.Height;
114.417 +
114.418 + if (this.LegendOrientation == LegendOrientation.Horizontal)
114.419 + {
114.420 + // Add spacing between items
114.421 + if (x > this.LegendPadding)
114.422 + {
114.423 + x += this.LegendItemSpacing;
114.424 + }
114.425 +
114.426 + // Check if the item is too large to fit within the available width
114.427 + if (x + itemWidth > availableWidth - this.LegendPadding + Epsilon)
114.428 + {
114.429 + // new line
114.430 + x = this.LegendPadding;
114.431 + y += lineHeight;
114.432 + lineHeight = 0;
114.433 + }
114.434 +
114.435 + // Update the max size of the current line
114.436 + lineHeight = Math.Max(lineHeight, textSize.Height);
114.437 +
114.438 + if (!measureOnly)
114.439 + {
114.440 + seriesToRender.Add(s, new OxyRect(rect.Left + x, rect.Top + y, itemWidth, itemHeight));
114.441 + }
114.442 +
114.443 + x += itemWidth;
114.444 +
114.445 + // Update the max width of the legend box
114.446 + size.Width = Math.Max(size.Width, x);
114.447 +
114.448 + // Update the max height of the legend box
114.449 + size.Height = Math.Max(size.Height, y + textSize.Height);
114.450 + }
114.451 + else
114.452 + {
114.453 + if (y + itemHeight > availableHeight - this.LegendPadding + Epsilon)
114.454 + {
114.455 + renderItems();
114.456 +
114.457 + y = top;
114.458 + x += maxItemWidth + this.LegendColumnSpacing;
114.459 + maxItemWidth = 0;
114.460 + }
114.461 +
114.462 + if (!measureOnly)
114.463 + {
114.464 + seriesToRender.Add(s, new OxyRect(rect.Left + x, rect.Top + y, itemWidth, itemHeight));
114.465 + }
114.466 +
114.467 + y += itemHeight;
114.468 +
114.469 + // Update the max size of the items in the current column
114.470 + maxItemWidth = Math.Max(maxItemWidth, itemWidth);
114.471 +
114.472 + // Update the max width of the legend box
114.473 + size.Width = Math.Max(size.Width, x + itemWidth);
114.474 +
114.475 + // Update the max height of the legend box
114.476 + size.Height = Math.Max(size.Height, y);
114.477 + }
114.478 + }
114.479 +
114.480 + renderItems();
114.481 +
114.482 + if (size.Width > 0)
114.483 + {
114.484 + size.Width += this.LegendPadding;
114.485 + }
114.486 +
114.487 + if (size.Height > 0)
114.488 + {
114.489 + size.Height += this.LegendPadding;
114.490 + }
114.491 +
114.492 + if (size.Width > availableWidth)
114.493 + {
114.494 + size.Width = availableWidth;
114.495 + }
114.496 +
114.497 + if (size.Height > availableHeight)
114.498 + {
114.499 + size.Height = availableHeight;
114.500 + }
114.501 +
114.502 + if (!double.IsNaN(LegendMaxWidth) && size.Width > this.LegendMaxWidth)
114.503 + {
114.504 + size.Width = this.LegendMaxWidth;
114.505 + }
114.506 +
114.507 + return size;
114.508 + }
114.509 + }
114.510 +}
114.511 \ No newline at end of file
115.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
115.2 +++ b/External/OxyPlot/OxyPlot/PlotModel/PlotModel.MouseEvents.cs Sat Jun 08 16:53:22 2013 +0000
115.3 @@ -0,0 +1,202 @@
115.4 +// --------------------------------------------------------------------------------------------------------------------
115.5 +// <copyright file="PlotModel.MouseEvents.cs" company="OxyPlot">
115.6 +// The MIT License (MIT)
115.7 +//
115.8 +// Copyright (c) 2012 Oystein Bjorke
115.9 +//
115.10 +// Permission is hereby granted, free of charge, to any person obtaining a
115.11 +// copy of this software and associated documentation files (the
115.12 +// "Software"), to deal in the Software without restriction, including
115.13 +// without limitation the rights to use, copy, modify, merge, publish,
115.14 +// distribute, sublicense, and/or sell copies of the Software, and to
115.15 +// permit persons to whom the Software is furnished to do so, subject to
115.16 +// the following conditions:
115.17 +//
115.18 +// The above copyright notice and this permission notice shall be included
115.19 +// in all copies or substantial portions of the Software.
115.20 +//
115.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
115.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
115.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
115.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
115.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
115.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
115.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
115.28 +// </copyright>
115.29 +// <summary>
115.30 +// Partial PlotModel class - this file contains mouse events and handlers.
115.31 +// </summary>
115.32 +// --------------------------------------------------------------------------------------------------------------------
115.33 +namespace OxyPlot
115.34 +{
115.35 + using System;
115.36 + using System.Linq;
115.37 +
115.38 + public partial class PlotModel
115.39 + {
115.40 + /// <summary>
115.41 + /// The mouse hit tolerance.
115.42 + /// </summary>
115.43 + private const double MouseHitTolerance = 10;
115.44 +
115.45 + /// <summary>
115.46 + /// The current mouse events element.
115.47 + /// </summary>
115.48 + private UIPlotElement currentMouseEventElement;
115.49 +
115.50 + /// <summary>
115.51 + /// Occurs when a mouse button is pressed down on the model.
115.52 + /// </summary>
115.53 + public event EventHandler<OxyMouseEventArgs> MouseDown;
115.54 +
115.55 + /// <summary>
115.56 + /// Occurs when the mouse is moved on the plot element (only occurs after MouseDown).
115.57 + /// </summary>
115.58 + public event EventHandler<OxyMouseEventArgs> MouseMove;
115.59 +
115.60 + /// <summary>
115.61 + /// Occurs when the mouse button is released on the plot element.
115.62 + /// </summary>
115.63 + public event EventHandler<OxyMouseEventArgs> MouseUp;
115.64 +
115.65 + /// <summary>
115.66 + /// Handles the mouse down event.
115.67 + /// </summary>
115.68 + /// <param name="sender">
115.69 + /// The sender.
115.70 + /// </param>
115.71 + /// <param name="e">
115.72 + /// The <see cref="OxyPlot.OxyMouseEventArgs"/> instance containing the event data.
115.73 + /// </param>
115.74 + public void HandleMouseDown(object sender, OxyMouseEventArgs e)
115.75 + {
115.76 + // Revert the order to handle the top-level elements first
115.77 + foreach (var element in this.GetElements().Reverse())
115.78 + {
115.79 + var uiElement = element as UIPlotElement;
115.80 + if (uiElement == null)
115.81 + {
115.82 + continue;
115.83 + }
115.84 +
115.85 + var result = uiElement.HitTest(e.Position, MouseHitTolerance);
115.86 + if (result != null)
115.87 + {
115.88 + e.HitTestResult = result;
115.89 + uiElement.OnMouseDown(sender, e);
115.90 + if (e.Handled)
115.91 + {
115.92 + this.currentMouseEventElement = uiElement;
115.93 + }
115.94 + }
115.95 +
115.96 + if (e.Handled)
115.97 + {
115.98 + break;
115.99 + }
115.100 + }
115.101 +
115.102 + if (!e.Handled)
115.103 + {
115.104 + this.OnMouseDown(sender, e);
115.105 + }
115.106 + }
115.107 +
115.108 + /// <summary>
115.109 + /// Handles the mouse move event.
115.110 + /// </summary>
115.111 + /// <param name="sender">
115.112 + /// The sender.
115.113 + /// </param>
115.114 + /// <param name="e">
115.115 + /// The <see cref="OxyPlot.OxyMouseEventArgs"/> instance containing the event data.
115.116 + /// </param>
115.117 + public void HandleMouseMove(object sender, OxyMouseEventArgs e)
115.118 + {
115.119 + if (this.currentMouseEventElement != null)
115.120 + {
115.121 + this.currentMouseEventElement.OnMouseMove(sender, e);
115.122 + }
115.123 +
115.124 + if (!e.Handled)
115.125 + {
115.126 + this.OnMouseMove(sender, e);
115.127 + }
115.128 + }
115.129 +
115.130 + /// <summary>
115.131 + /// Handles the mouse up event.
115.132 + /// </summary>
115.133 + /// <param name="sender">
115.134 + /// The sender.
115.135 + /// </param>
115.136 + /// <param name="e">
115.137 + /// The <see cref="OxyPlot.OxyMouseEventArgs"/> instance containing the event data.
115.138 + /// </param>
115.139 + public void HandleMouseUp(object sender, OxyMouseEventArgs e)
115.140 + {
115.141 + if (this.currentMouseEventElement != null)
115.142 + {
115.143 + this.currentMouseEventElement.OnMouseUp(sender, e);
115.144 + this.currentMouseEventElement = null;
115.145 + }
115.146 +
115.147 + if (!e.Handled)
115.148 + {
115.149 + this.OnMouseUp(sender, e);
115.150 + }
115.151 + }
115.152 +
115.153 + /// <summary>
115.154 + /// Raises the <see cref="MouseDown"/> event.
115.155 + /// </summary>
115.156 + /// <param name="sender">
115.157 + /// The sender.
115.158 + /// </param>
115.159 + /// <param name="e">
115.160 + /// The <see cref="OxyMouseEventArgs"/> instance containing the event data.
115.161 + /// </param>
115.162 + protected virtual void OnMouseDown(object sender, OxyMouseEventArgs e)
115.163 + {
115.164 + if (this.MouseDown != null && !e.Handled)
115.165 + {
115.166 + this.MouseDown(sender, e);
115.167 + }
115.168 + }
115.169 +
115.170 + /// <summary>
115.171 + /// Raises the <see cref="MouseMove"/> event.
115.172 + /// </summary>
115.173 + /// <param name="sender">
115.174 + /// The sender.
115.175 + /// </param>
115.176 + /// <param name="e">
115.177 + /// The <see cref="OxyMouseEventArgs"/> instance containing the event data.
115.178 + /// </param>
115.179 + protected virtual void OnMouseMove(object sender, OxyMouseEventArgs e)
115.180 + {
115.181 + if (this.MouseMove != null)
115.182 + {
115.183 + this.MouseMove(sender, e);
115.184 + }
115.185 + }
115.186 +
115.187 + /// <summary>
115.188 + /// Raises the <see cref="MouseUp"/> event.
115.189 + /// </summary>
115.190 + /// <param name="sender">
115.191 + /// The sender.
115.192 + /// </param>
115.193 + /// <param name="e">
115.194 + /// The <see cref="OxyMouseEventArgs"/> instance containing the event data.
115.195 + /// </param>
115.196 + protected virtual void OnMouseUp(object sender, OxyMouseEventArgs e)
115.197 + {
115.198 + if (this.MouseUp != null)
115.199 + {
115.200 + this.MouseUp(sender, e);
115.201 + }
115.202 + }
115.203 +
115.204 + }
115.205 +}
115.206 \ No newline at end of file
116.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
116.2 +++ b/External/OxyPlot/OxyPlot/PlotModel/PlotModel.Rendering.cs Sat Jun 08 16:53:22 2013 +0000
116.3 @@ -0,0 +1,481 @@
116.4 +// --------------------------------------------------------------------------------------------------------------------
116.5 +// <copyright file="PlotModel.Rendering.cs" company="OxyPlot">
116.6 +// The MIT License (MIT)
116.7 +//
116.8 +// Copyright (c) 2012 Oystein Bjorke
116.9 +//
116.10 +// Permission is hereby granted, free of charge, to any person obtaining a
116.11 +// copy of this software and associated documentation files (the
116.12 +// "Software"), to deal in the Software without restriction, including
116.13 +// without limitation the rights to use, copy, modify, merge, publish,
116.14 +// distribute, sublicense, and/or sell copies of the Software, and to
116.15 +// permit persons to whom the Software is furnished to do so, subject to
116.16 +// the following conditions:
116.17 +//
116.18 +// The above copyright notice and this permission notice shall be included
116.19 +// in all copies or substantial portions of the Software.
116.20 +//
116.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
116.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
116.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
116.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
116.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
116.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
116.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
116.28 +// </copyright>
116.29 +// <summary>
116.30 +// Partial PlotModel class - this file contains rendering methods.
116.31 +// </summary>
116.32 +// --------------------------------------------------------------------------------------------------------------------
116.33 +namespace OxyPlot
116.34 +{
116.35 + using System;
116.36 + using System.Collections.Generic;
116.37 + using System.Linq;
116.38 +
116.39 + using OxyPlot.Annotations;
116.40 + using OxyPlot.Axes;
116.41 + using OxyPlot.Series;
116.42 +
116.43 + public partial class PlotModel
116.44 + {
116.45 + /// <summary>
116.46 + /// Renders the plot with the specified rendering context.
116.47 + /// </summary>
116.48 + /// <param name="rc">The rendering context.</param>
116.49 + /// <param name="width">The width.</param>
116.50 + /// <param name="height">The height.</param>
116.51 + public void Render(IRenderContext rc, double width, double height)
116.52 + {
116.53 + lock (this.syncRoot)
116.54 + {
116.55 + if (width <= 0 || height <= 0)
116.56 + {
116.57 + return;
116.58 + }
116.59 +
116.60 + this.Width = width;
116.61 + this.Height = height;
116.62 +
116.63 + this.ActualPlotMargins = this.PlotMargins;
116.64 + this.EnsureLegendProperties();
116.65 +
116.66 + while (true)
116.67 + {
116.68 + this.UpdatePlotArea(rc);
116.69 + this.UpdateAxisTransforms();
116.70 + this.UpdateIntervals();
116.71 + if (!this.AutoAdjustPlotMargins)
116.72 + {
116.73 + break;
116.74 + }
116.75 +
116.76 + if (!this.AdjustPlotMargins(rc))
116.77 + {
116.78 + break;
116.79 + }
116.80 + }
116.81 +
116.82 + if (this.PlotType == PlotType.Cartesian)
116.83 + {
116.84 + this.EnforceCartesianTransforms();
116.85 + this.UpdateIntervals();
116.86 + }
116.87 +
116.88 + this.RenderBackgrounds(rc);
116.89 + this.RenderAnnotations(rc, AnnotationLayer.BelowAxes);
116.90 + this.RenderAxes(rc, AxisLayer.BelowSeries);
116.91 + this.RenderAnnotations(rc, AnnotationLayer.BelowSeries);
116.92 + this.RenderSeries(rc);
116.93 + this.RenderAnnotations(rc, AnnotationLayer.AboveSeries);
116.94 + this.RenderTitle(rc);
116.95 + this.RenderBox(rc);
116.96 + this.RenderAxes(rc, AxisLayer.AboveSeries);
116.97 +
116.98 + if (this.IsLegendVisible)
116.99 + {
116.100 + this.RenderLegends(rc, this.LegendArea);
116.101 + }
116.102 + }
116.103 + }
116.104 +
116.105 + /// <summary>
116.106 + /// Calculates the maximum size of the specified axes.
116.107 + /// </summary>
116.108 + /// <param name="rc">
116.109 + /// The render context.
116.110 + /// </param>
116.111 + /// <param name="axesOfPositionTier">
116.112 + /// The axes of position tier.
116.113 + /// </param>
116.114 + /// <returns>
116.115 + /// The maximum size.
116.116 + /// </returns>
116.117 + private static double MaxSizeOfPositionTier(IRenderContext rc, IEnumerable<Axis> axesOfPositionTier)
116.118 + {
116.119 + double maxSizeOfPositionTier = 0;
116.120 + foreach (var axis in axesOfPositionTier)
116.121 + {
116.122 + OxySize size = axis.Measure(rc);
116.123 + if (axis.IsHorizontal())
116.124 + {
116.125 + if (size.Height > maxSizeOfPositionTier)
116.126 + {
116.127 + maxSizeOfPositionTier = size.Height;
116.128 + }
116.129 + }
116.130 + else
116.131 + {
116.132 + if (size.Width > maxSizeOfPositionTier)
116.133 + {
116.134 + maxSizeOfPositionTier = size.Width;
116.135 + }
116.136 + }
116.137 + }
116.138 +
116.139 + return maxSizeOfPositionTier;
116.140 + }
116.141 +
116.142 + /// <summary>
116.143 + /// Adjust the plot margins.
116.144 + /// </summary>
116.145 + /// <param name="rc">
116.146 + /// The render context.
116.147 + /// </param>
116.148 + /// <returns>
116.149 + /// The adjust plot margins.
116.150 + /// </returns>
116.151 + private bool AdjustPlotMargins(IRenderContext rc)
116.152 + {
116.153 + bool isAdjusted = false;
116.154 + var newPlotMargins = new Dictionary<AxisPosition, double>
116.155 + {
116.156 + { AxisPosition.Left, this.ActualPlotMargins.Left },
116.157 + { AxisPosition.Top, this.ActualPlotMargins.Top },
116.158 + { AxisPosition.Right, this.ActualPlotMargins.Right },
116.159 + { AxisPosition.Bottom, this.ActualPlotMargins.Bottom }
116.160 + };
116.161 +
116.162 + for (var position = AxisPosition.Left; position <= AxisPosition.Bottom; position++)
116.163 + {
116.164 + double maxValueOfPositionTier = 0;
116.165 + var axesOfPosition = this.Axes.Where(a => a.Position == position).ToList();
116.166 + foreach (var positionTier in axesOfPosition.Select(a => a.PositionTier).Distinct().OrderBy(l => l))
116.167 + {
116.168 + var axesOfPositionTier = axesOfPosition.Where(a => a.PositionTier == positionTier).ToList();
116.169 + double maxSizeOfPositionTier = MaxSizeOfPositionTier(rc, axesOfPositionTier);
116.170 + double minValueOfPositionTier = maxValueOfPositionTier;
116.171 +
116.172 + if (Math.Abs(maxValueOfPositionTier) > 1e-5)
116.173 + {
116.174 + maxValueOfPositionTier += this.AxisTierDistance;
116.175 + }
116.176 +
116.177 + maxValueOfPositionTier += maxSizeOfPositionTier;
116.178 +
116.179 + foreach (Axis axis in axesOfPositionTier)
116.180 + {
116.181 + axis.PositionTierSize = maxSizeOfPositionTier;
116.182 + axis.PositionTierMinShift = minValueOfPositionTier;
116.183 + axis.PositionTierMaxShift = maxValueOfPositionTier;
116.184 + }
116.185 + }
116.186 +
116.187 + if (maxValueOfPositionTier > newPlotMargins[position])
116.188 + {
116.189 + newPlotMargins[position] = maxValueOfPositionTier;
116.190 + isAdjusted = true;
116.191 + }
116.192 + }
116.193 +
116.194 + if (isAdjusted)
116.195 + {
116.196 + this.ActualPlotMargins = new OxyThickness(
116.197 + newPlotMargins[AxisPosition.Left],
116.198 + newPlotMargins[AxisPosition.Top],
116.199 + newPlotMargins[AxisPosition.Right],
116.200 + newPlotMargins[AxisPosition.Bottom]);
116.201 + }
116.202 +
116.203 + return isAdjusted;
116.204 + }
116.205 +
116.206 + /// <summary>
116.207 + /// Measures the size of the title and subtitle.
116.208 + /// </summary>
116.209 + /// <param name="rc">
116.210 + /// The rendering context.
116.211 + /// </param>
116.212 + /// <returns>
116.213 + /// Size of the titles.
116.214 + /// </returns>
116.215 + private OxySize MeasureTitles(IRenderContext rc)
116.216 + {
116.217 + OxySize size1 = rc.MeasureText(this.Title, this.ActualTitleFont, this.TitleFontSize, this.TitleFontWeight);
116.218 + OxySize size2 = rc.MeasureText(
116.219 + this.Subtitle, this.SubtitleFont ?? this.ActualSubtitleFont, this.SubtitleFontSize, this.SubtitleFontWeight);
116.220 + double height = size1.Height + size2.Height;
116.221 + double width = Math.Max(size1.Width, size2.Width);
116.222 + return new OxySize(width, height);
116.223 + }
116.224 +
116.225 + /// <summary>
116.226 + /// Renders the annotations.
116.227 + /// </summary>
116.228 + /// <param name="rc">
116.229 + /// The render context.
116.230 + /// </param>
116.231 + /// <param name="layer">
116.232 + /// The layer.
116.233 + /// </param>
116.234 + private void RenderAnnotations(IRenderContext rc, AnnotationLayer layer)
116.235 + {
116.236 + foreach (var a in this.Annotations.Where(a => a.Layer == layer))
116.237 + {
116.238 + a.Render(rc, this);
116.239 + }
116.240 + }
116.241 +
116.242 + /// <summary>
116.243 + /// Renders the axes.
116.244 + /// </summary>
116.245 + /// <param name="rc">
116.246 + /// The render context.
116.247 + /// </param>
116.248 + /// <param name="layer">
116.249 + /// The layer.
116.250 + /// </param>
116.251 + private void RenderAxes(IRenderContext rc, AxisLayer layer)
116.252 + {
116.253 + for (int i = 0; i < 2; i++)
116.254 + {
116.255 + foreach (var a in this.Axes)
116.256 + {
116.257 + if (a.IsAxisVisible && a.Layer == layer)
116.258 + {
116.259 + a.Render(rc, this, layer, i);
116.260 + }
116.261 + }
116.262 + }
116.263 + }
116.264 +
116.265 + /// <summary>
116.266 + /// Renders the series backgrounds.
116.267 + /// </summary>
116.268 + /// <param name="rc">
116.269 + /// The render context.
116.270 + /// </param>
116.271 + private void RenderBackgrounds(IRenderContext rc)
116.272 + {
116.273 + // Render the main background of the plot area (only if there are axes)
116.274 + // The border is rendered by DrawRectangleAsPolygon to ensure that it is pixel aligned with the tick marks.
116.275 + if (this.Axes.Count > 0 && this.PlotAreaBackground != null)
116.276 + {
116.277 + rc.DrawRectangleAsPolygon(this.PlotArea, this.PlotAreaBackground, null, 0);
116.278 + }
116.279 +
116.280 + foreach (var s in this.VisibleSeries)
116.281 + {
116.282 + var s2 = s as XYAxisSeries;
116.283 + if (s2 == null || s2.Background == null)
116.284 + {
116.285 + continue;
116.286 + }
116.287 +
116.288 + rc.DrawRectangle(s2.GetScreenRectangle(), s2.Background, null, 0);
116.289 + }
116.290 + }
116.291 +
116.292 + /// <summary>
116.293 + /// Renders the border around the plot area.
116.294 + /// </summary>
116.295 + /// <remarks>
116.296 + /// The border will only by rendered if there are axes in the plot.
116.297 + /// </remarks>
116.298 + /// <param name="rc">
116.299 + /// The render context.
116.300 + /// </param>
116.301 + private void RenderBox(IRenderContext rc)
116.302 + {
116.303 + // The border is rendered by DrawBox to ensure that it is pixel aligned with the tick marks (cannot use DrawRectangle here).
116.304 + if (this.Axes.Count > 0)
116.305 + {
116.306 + rc.DrawRectangleAsPolygon(this.PlotArea, null, this.PlotAreaBorderColor, this.PlotAreaBorderThickness);
116.307 + }
116.308 + }
116.309 +
116.310 + /// <summary>
116.311 + /// Renders the series.
116.312 + /// </summary>
116.313 + /// <param name="rc">
116.314 + /// The render context.
116.315 + /// </param>
116.316 + private void RenderSeries(IRenderContext rc)
116.317 + {
116.318 + // Update undefined colors
116.319 + this.ResetDefaultColor();
116.320 + foreach (var s in this.VisibleSeries)
116.321 + {
116.322 + s.SetDefaultValues(this);
116.323 + }
116.324 +
116.325 + foreach (var s in this.VisibleSeries)
116.326 + {
116.327 + s.Render(rc, this);
116.328 + }
116.329 + }
116.330 +
116.331 + /// <summary>
116.332 + /// Renders the title and subtitle.
116.333 + /// </summary>
116.334 + /// <param name="rc">
116.335 + /// The render context.
116.336 + /// </param>
116.337 + private void RenderTitle(IRenderContext rc)
116.338 + {
116.339 + OxySize size1 = rc.MeasureText(this.Title, this.ActualTitleFont, this.TitleFontSize, this.TitleFontWeight);
116.340 + rc.MeasureText(
116.341 + this.Subtitle, this.SubtitleFont ?? this.ActualSubtitleFont, this.SubtitleFontSize, this.SubtitleFontWeight);
116.342 +
116.343 + // double height = size1.Height + size2.Height;
116.344 + // double dy = (TitleArea.Top+TitleArea.Bottom-height)*0.5;
116.345 + double dy = this.TitleArea.Top;
116.346 + double dx = (this.TitleArea.Left + this.TitleArea.Right) * 0.5;
116.347 +
116.348 + if (!string.IsNullOrEmpty(this.Title))
116.349 + {
116.350 + rc.DrawMathText(
116.351 + new ScreenPoint(dx, dy),
116.352 + this.Title,
116.353 + this.TitleColor ?? this.TextColor,
116.354 + this.ActualTitleFont,
116.355 + this.TitleFontSize,
116.356 + this.TitleFontWeight,
116.357 + 0,
116.358 + HorizontalAlignment.Center,
116.359 + VerticalAlignment.Top);
116.360 + dy += size1.Height;
116.361 + }
116.362 +
116.363 + if (!string.IsNullOrEmpty(this.Subtitle))
116.364 + {
116.365 + rc.DrawMathText(
116.366 + new ScreenPoint(dx, dy),
116.367 + this.Subtitle,
116.368 + this.SubtitleColor ?? this.TextColor,
116.369 + this.ActualSubtitleFont,
116.370 + this.SubtitleFontSize,
116.371 + this.SubtitleFontWeight,
116.372 + 0,
116.373 + HorizontalAlignment.Center,
116.374 + VerticalAlignment.Top);
116.375 + }
116.376 + }
116.377 +
116.378 + /// <summary>
116.379 + /// Calculates the plot area (subtract padding, title size and outside legends)
116.380 + /// </summary>
116.381 + /// <param name="rc">
116.382 + /// The rendering context.
116.383 + /// </param>
116.384 + private void UpdatePlotArea(IRenderContext rc)
116.385 + {
116.386 + var plotArea = new OxyRect(
116.387 + this.Padding.Left,
116.388 + this.Padding.Top,
116.389 + this.Width - this.Padding.Left - this.Padding.Right,
116.390 + this.Height - this.Padding.Top - this.Padding.Bottom);
116.391 +
116.392 + var titleSize = this.MeasureTitles(rc);
116.393 +
116.394 + if (titleSize.Height > 0)
116.395 + {
116.396 + double titleHeight = titleSize.Height + this.TitlePadding;
116.397 + plotArea.Height -= titleHeight;
116.398 + plotArea.Top += titleHeight;
116.399 + }
116.400 +
116.401 + plotArea.Top += this.ActualPlotMargins.Top;
116.402 + plotArea.Height -= this.ActualPlotMargins.Top;
116.403 +
116.404 + plotArea.Height -= this.ActualPlotMargins.Bottom;
116.405 +
116.406 + plotArea.Left += this.ActualPlotMargins.Left;
116.407 + plotArea.Width -= this.ActualPlotMargins.Left;
116.408 +
116.409 + plotArea.Width -= this.ActualPlotMargins.Right;
116.410 +
116.411 + // Find the available size for the legend box
116.412 + double availableLegendWidth = plotArea.Width;
116.413 + double availableLegendHeight = plotArea.Height;
116.414 + if (this.LegendPlacement == LegendPlacement.Inside)
116.415 + {
116.416 + availableLegendWidth -= this.LegendMargin * 2;
116.417 + availableLegendHeight -= this.LegendMargin * 2;
116.418 + }
116.419 +
116.420 + if (availableLegendWidth < 0)
116.421 + {
116.422 + availableLegendWidth = 0;
116.423 + }
116.424 +
116.425 + if (availableLegendHeight < 0)
116.426 + {
116.427 + availableLegendHeight = 0;
116.428 + }
116.429 +
116.430 + // Calculate the size of the legend box
116.431 + var legendSize = this.MeasureLegends(rc, new OxySize(availableLegendWidth, availableLegendHeight));
116.432 +
116.433 + // Adjust the plot area after the size of the legend box has been calculated
116.434 + if (this.IsLegendVisible && this.LegendPlacement == LegendPlacement.Outside)
116.435 + {
116.436 + switch (this.LegendPosition)
116.437 + {
116.438 + case LegendPosition.LeftTop:
116.439 + case LegendPosition.LeftMiddle:
116.440 + case LegendPosition.LeftBottom:
116.441 + plotArea.Left += legendSize.Width + this.LegendMargin;
116.442 + plotArea.Width -= legendSize.Width + this.LegendMargin;
116.443 + break;
116.444 + case LegendPosition.RightTop:
116.445 + case LegendPosition.RightMiddle:
116.446 + case LegendPosition.RightBottom:
116.447 + plotArea.Width -= legendSize.Width + this.LegendMargin;
116.448 + break;
116.449 + case LegendPosition.TopLeft:
116.450 + case LegendPosition.TopCenter:
116.451 + case LegendPosition.TopRight:
116.452 + plotArea.Top += legendSize.Height + this.LegendMargin;
116.453 + plotArea.Height -= legendSize.Height + this.LegendMargin;
116.454 + break;
116.455 + case LegendPosition.BottomLeft:
116.456 + case LegendPosition.BottomCenter:
116.457 + case LegendPosition.BottomRight:
116.458 + plotArea.Height -= legendSize.Height + this.LegendMargin;
116.459 + break;
116.460 + }
116.461 + }
116.462 +
116.463 + // Ensure the plot area is valid
116.464 + if (plotArea.Height < 0)
116.465 + {
116.466 + plotArea.Bottom = plotArea.Top + 1;
116.467 + }
116.468 +
116.469 + if (plotArea.Width < 0)
116.470 + {
116.471 + plotArea.Right = plotArea.Left + 1;
116.472 + }
116.473 +
116.474 + this.PlotArea = plotArea;
116.475 + this.PlotAndAxisArea = new OxyRect(
116.476 + plotArea.Left - this.ActualPlotMargins.Left,
116.477 + plotArea.Top - this.ActualPlotMargins.Top,
116.478 + plotArea.Width + this.ActualPlotMargins.Left + this.ActualPlotMargins.Right,
116.479 + plotArea.Height + this.ActualPlotMargins.Top + this.ActualPlotMargins.Bottom);
116.480 + this.TitleArea = new OxyRect(this.PlotArea.Left, this.Padding.Top, this.PlotArea.Width, titleSize.Height + (this.TitlePadding * 2));
116.481 + this.LegendArea = this.GetLegendRectangle(legendSize);
116.482 + }
116.483 + }
116.484 +}
116.485 \ No newline at end of file
117.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
117.2 +++ b/External/OxyPlot/OxyPlot/PlotModel/PlotModel.cs Sat Jun 08 16:53:22 2013 +0000
117.3 @@ -0,0 +1,1485 @@
117.4 +// --------------------------------------------------------------------------------------------------------------------
117.5 +// <copyright file="PlotModel.cs" company="OxyPlot">
117.6 +// The MIT License (MIT)
117.7 +//
117.8 +// Copyright (c) 2012 Oystein Bjorke
117.9 +//
117.10 +// Permission is hereby granted, free of charge, to any person obtaining a
117.11 +// copy of this software and associated documentation files (the
117.12 +// "Software"), to deal in the Software without restriction, including
117.13 +// without limitation the rights to use, copy, modify, merge, publish,
117.14 +// distribute, sublicense, and/or sell copies of the Software, and to
117.15 +// permit persons to whom the Software is furnished to do so, subject to
117.16 +// the following conditions:
117.17 +//
117.18 +// The above copyright notice and this permission notice shall be included
117.19 +// in all copies or substantial portions of the Software.
117.20 +//
117.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
117.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
117.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
117.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
117.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
117.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
117.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
117.28 +// </copyright>
117.29 +// <summary>
117.30 +// Plot coordinate system type
117.31 +// </summary>
117.32 +// --------------------------------------------------------------------------------------------------------------------
117.33 +namespace OxyPlot
117.34 +{
117.35 + using System;
117.36 + using System.Collections.Generic;
117.37 + using System.Collections.ObjectModel;
117.38 + using System.Diagnostics;
117.39 + using System.Globalization;
117.40 + using System.IO;
117.41 + using System.Linq;
117.42 + using System.Reflection;
117.43 +
117.44 + using OxyPlot.Annotations;
117.45 + using OxyPlot.Axes;
117.46 + using OxyPlot.Reporting;
117.47 + using OxyPlot.Series;
117.48 +
117.49 + /// <summary>
117.50 + /// Specifies the coordinate system type.
117.51 + /// </summary>
117.52 + public enum PlotType
117.53 + {
117.54 + /// <summary>
117.55 + /// XY coordinate system - two perpendicular axes
117.56 + /// </summary>
117.57 + XY,
117.58 +
117.59 + /// <summary>
117.60 + /// Cartesian coordinate system - perpendicular axes with the same scaling.
117.61 + /// </summary>
117.62 + /// <remarks>
117.63 + /// See http://en.wikipedia.org/wiki/Cartesian_coordinate_system
117.64 + /// </remarks>
117.65 + Cartesian,
117.66 +
117.67 + /// <summary>
117.68 + /// Polar coordinate system - with radial and angular axes
117.69 + /// </summary>
117.70 + /// <remarks>
117.71 + /// See http://en.wikipedia.org/wiki/Polar_coordinate_system
117.72 + /// </remarks>
117.73 + Polar
117.74 + }
117.75 +
117.76 + /// <summary>
117.77 + /// Specifies the placement of the legend box.
117.78 + /// </summary>
117.79 + public enum LegendPlacement
117.80 + {
117.81 + /// <summary>
117.82 + /// Place the legends inside the plot area.
117.83 + /// </summary>
117.84 + Inside,
117.85 +
117.86 + /// <summary>
117.87 + /// Place the legends outside the plot area.
117.88 + /// </summary>
117.89 + Outside
117.90 + }
117.91 +
117.92 + /// <summary>
117.93 + /// Specifies the position of the legend box.
117.94 + /// </summary>
117.95 + public enum LegendPosition
117.96 + {
117.97 + /// <summary>
117.98 + /// Place the legend box in the top-left corner.
117.99 + /// </summary>
117.100 + TopLeft,
117.101 +
117.102 + /// <summary>
117.103 + /// Place the legend box centered at the top.
117.104 + /// </summary>
117.105 + TopCenter,
117.106 +
117.107 + /// <summary>
117.108 + /// Place the legend box in the top-right corner.
117.109 + /// </summary>
117.110 + TopRight,
117.111 +
117.112 + /// <summary>
117.113 + /// Place the legend box in the bottom-left corner.
117.114 + /// </summary>
117.115 + BottomLeft,
117.116 +
117.117 + /// <summary>
117.118 + /// Place the legend box centered at the bottom.
117.119 + /// </summary>
117.120 + BottomCenter,
117.121 +
117.122 + /// <summary>
117.123 + /// Place the legend box in the bottom-right corner.
117.124 + /// </summary>
117.125 + BottomRight,
117.126 +
117.127 + /// <summary>
117.128 + /// Place the legend box in the left-top corner.
117.129 + /// </summary>
117.130 + LeftTop,
117.131 +
117.132 + /// <summary>
117.133 + /// Place the legend box centered at the left.
117.134 + /// </summary>
117.135 + LeftMiddle,
117.136 +
117.137 + /// <summary>
117.138 + /// Place the legend box in the left-bottom corner.
117.139 + /// </summary>
117.140 + LeftBottom,
117.141 +
117.142 + /// <summary>
117.143 + /// Place the legend box in the right-top corner.
117.144 + /// </summary>
117.145 + RightTop,
117.146 +
117.147 + /// <summary>
117.148 + /// Place the legend box centered at the right.
117.149 + /// </summary>
117.150 + RightMiddle,
117.151 +
117.152 + /// <summary>
117.153 + /// Place the legend box in the right-bottom corner.
117.154 + /// </summary>
117.155 + RightBottom
117.156 + }
117.157 +
117.158 + /// <summary>
117.159 + /// Specifies the orientation of the items in the legend box.
117.160 + /// </summary>
117.161 + public enum LegendOrientation
117.162 + {
117.163 + /// <summary>
117.164 + /// Orient the items horizontally.
117.165 + /// </summary>
117.166 + Horizontal,
117.167 +
117.168 + /// <summary>
117.169 + /// Orient the items vertically.
117.170 + /// </summary>
117.171 + Vertical
117.172 + }
117.173 +
117.174 + /// <summary>
117.175 + /// Specifies the item order of the legends.
117.176 + /// </summary>
117.177 + public enum LegendItemOrder
117.178 + {
117.179 + /// <summary>
117.180 + /// Render the items in the normal order.
117.181 + /// </summary>
117.182 + Normal,
117.183 +
117.184 + /// <summary>
117.185 + /// Render the items in the reverse order.
117.186 + /// </summary>
117.187 + Reverse
117.188 + }
117.189 +
117.190 + /// <summary>
117.191 + /// Specifies the placement of the legend symbols.
117.192 + /// </summary>
117.193 + public enum LegendSymbolPlacement
117.194 + {
117.195 + /// <summary>
117.196 + /// Render symbols to the left of the labels.
117.197 + /// </summary>
117.198 + Left,
117.199 +
117.200 + /// <summary>
117.201 + /// Render symbols to the right of the labels.
117.202 + /// </summary>
117.203 + Right
117.204 + }
117.205 +
117.206 + /// <summary>
117.207 + /// Represents a plot (including axes, series and annotations).
117.208 + /// </summary>
117.209 + public partial class PlotModel
117.210 + {
117.211 + /// <summary>
117.212 + /// The default selection color.
117.213 + /// </summary>
117.214 + internal static readonly OxyColor DefaultSelectionColor = OxyColors.Yellow;
117.215 +
117.216 + /// <summary>
117.217 + /// The default font.
117.218 + /// </summary>
117.219 + private const string PrivateDefaultFont = "Segoe UI";
117.220 +
117.221 + /// <summary>
117.222 + /// The current color index.
117.223 + /// </summary>
117.224 + private int currentColorIndex;
117.225 +
117.226 + /// <summary>
117.227 + /// Initializes a new instance of the <see cref="PlotModel" /> class.
117.228 + /// </summary>
117.229 + public PlotModel()
117.230 + {
117.231 + this.Axes = new Collection<Axis>();
117.232 + this.Series = new Collection<OxyPlot.Series.Series>();
117.233 + this.Annotations = new Collection<Annotation>();
117.234 +
117.235 + this.PlotType = PlotType.XY;
117.236 +
117.237 + this.PlotMargins = new OxyThickness(60, 4, 4, 40);
117.238 + this.Padding = new OxyThickness(8, 8, 16, 8);
117.239 + this.AutoAdjustPlotMargins = true;
117.240 +
117.241 + this.DefaultFont = PrivateDefaultFont;
117.242 + this.DefaultFontSize = 12;
117.243 +
117.244 + this.TitleFont = null;
117.245 + this.TitleFontSize = 18;
117.246 + this.TitleFontWeight = FontWeights.Bold;
117.247 + this.SubtitleFont = null;
117.248 + this.SubtitleFontSize = 14;
117.249 + this.SubtitleFontWeight = FontWeights.Normal;
117.250 + this.TitlePadding = 6;
117.251 +
117.252 + this.TextColor = OxyColors.Black;
117.253 + this.PlotAreaBorderColor = OxyColors.Black;
117.254 + this.PlotAreaBorderThickness = 1;
117.255 +
117.256 + this.IsLegendVisible = true;
117.257 + this.LegendTitleFont = null;
117.258 + this.LegendTitleFontSize = 12;
117.259 + this.LegendTitleFontWeight = FontWeights.Bold;
117.260 + this.LegendFont = null;
117.261 + this.LegendFontSize = 12;
117.262 + this.LegendFontWeight = FontWeights.Normal;
117.263 + this.LegendSymbolLength = 16;
117.264 + this.LegendSymbolMargin = 4;
117.265 + this.LegendPadding = 8;
117.266 + this.LegendColumnSpacing = 8;
117.267 + this.LegendItemSpacing = 24;
117.268 + this.LegendMargin = 8;
117.269 +
117.270 + this.LegendBackground = null;
117.271 + this.LegendBorder = null;
117.272 + this.LegendBorderThickness = 1;
117.273 +
117.274 + this.LegendMaxWidth = double.NaN;
117.275 + this.LegendPlacement = LegendPlacement.Inside;
117.276 + this.LegendPosition = LegendPosition.RightTop;
117.277 + this.LegendOrientation = LegendOrientation.Vertical;
117.278 + this.LegendItemOrder = LegendItemOrder.Normal;
117.279 + this.LegendItemAlignment = HorizontalAlignment.Left;
117.280 + this.LegendSymbolPlacement = LegendSymbolPlacement.Left;
117.281 +
117.282 + this.DefaultColors = new List<OxyColor>
117.283 + {
117.284 + OxyColor.FromRgb(0x4E, 0x9A, 0x06),
117.285 + OxyColor.FromRgb(0xC8, 0x8D, 0x00),
117.286 + OxyColor.FromRgb(0xCC, 0x00, 0x00),
117.287 + OxyColor.FromRgb(0x20, 0x4A, 0x87),
117.288 + OxyColors.Red,
117.289 + OxyColors.Orange,
117.290 + OxyColors.Yellow,
117.291 + OxyColors.Green,
117.292 + OxyColors.Blue,
117.293 + OxyColors.Indigo,
117.294 + OxyColors.Violet
117.295 + };
117.296 +
117.297 + this.AxisTierDistance = 4.0;
117.298 + }
117.299 +
117.300 + /// <summary>
117.301 + /// Initializes a new instance of the <see cref="PlotModel"/> class.
117.302 + /// </summary>
117.303 + /// <param name="title">
117.304 + /// The title.
117.305 + /// </param>
117.306 + /// <param name="subtitle">
117.307 + /// The subtitle.
117.308 + /// </param>
117.309 + public PlotModel(string title, string subtitle = null)
117.310 + : this()
117.311 + {
117.312 + this.Title = title;
117.313 + this.Subtitle = subtitle;
117.314 + }
117.315 +
117.316 + /// <summary>
117.317 + /// The synchronization root object.
117.318 + /// </summary>
117.319 + private object syncRoot = new object();
117.320 +
117.321 + /// <summary>
117.322 + /// Gets an object that can be used to synchronize access to the PlotModel.
117.323 + /// </summary>
117.324 + /// <value>The sync root.</value>
117.325 + public object SyncRoot { get { return this.syncRoot; } }
117.326 +
117.327 + /// <summary>
117.328 + /// Occurs when the plot has been updated.
117.329 + /// </summary>
117.330 + public event EventHandler Updated;
117.331 +
117.332 + /// <summary>
117.333 + /// Occurs when the plot is about to be updated.
117.334 + /// </summary>
117.335 + public event EventHandler Updating;
117.336 +
117.337 + /// <summary>
117.338 + /// Gets or sets the default font.
117.339 + /// </summary>
117.340 + /// <value> The default font. </value>
117.341 + /// <remarks>
117.342 + /// This font is used for text on axes, series, legends and plot titles unless other fonts are specified.
117.343 + /// </remarks>
117.344 + public string DefaultFont { get; set; }
117.345 +
117.346 + /// <summary>
117.347 + /// Gets or sets the default size of the fonts.
117.348 + /// </summary>
117.349 + /// <value>
117.350 + /// The default size of the font.
117.351 + /// </value>
117.352 + public double DefaultFontSize { get; set; }
117.353 +
117.354 + /// <summary>
117.355 + /// Gets the actual culture.
117.356 + /// </summary>
117.357 + public CultureInfo ActualCulture
117.358 + {
117.359 + get
117.360 + {
117.361 + return this.Culture ?? CultureInfo.CurrentCulture;
117.362 + }
117.363 + }
117.364 +
117.365 + /// <summary>
117.366 + /// Gets the actual plot margins.
117.367 + /// </summary>
117.368 + /// <value> The actual plot margins. </value>
117.369 + public OxyThickness ActualPlotMargins { get; private set; }
117.370 +
117.371 + /// <summary>
117.372 + /// Gets the plot control that renders this plot.
117.373 + /// </summary>
117.374 + /// <remarks>
117.375 + /// Only one PlotControl can render the plot at the same time.
117.376 + /// </remarks>
117.377 + /// <value>The plot control.</value>
117.378 + public IPlotControl PlotControl { get; private set; }
117.379 +
117.380 + /// <summary>
117.381 + /// Gets or sets the annotations.
117.382 + /// </summary>
117.383 + /// <value> The annotations. </value>
117.384 + public Collection<Annotation> Annotations { get; set; }
117.385 +
117.386 + /// <summary>
117.387 + /// Gets or sets a value indicating whether to auto adjust plot margins.
117.388 + /// </summary>
117.389 + public bool AutoAdjustPlotMargins { get; set; }
117.390 +
117.391 + /// <summary>
117.392 + /// Gets or sets the axes.
117.393 + /// </summary>
117.394 + /// <value> The axes. </value>
117.395 + public Collection<Axis> Axes { get; set; }
117.396 +
117.397 + /// <summary>
117.398 + /// Gets or sets the color of the background of the plot.
117.399 + /// </summary>
117.400 + public OxyColor Background { get; set; }
117.401 +
117.402 + /// <summary>
117.403 + /// Gets or sets the culture.
117.404 + /// </summary>
117.405 + /// <value> The culture. </value>
117.406 + public CultureInfo Culture { get; set; }
117.407 +
117.408 + /// <summary>
117.409 + /// Gets or sets the default colors.
117.410 + /// </summary>
117.411 + /// <value> The default colors. </value>
117.412 + public IList<OxyColor> DefaultColors { get; set; }
117.413 +
117.414 + /// <summary>
117.415 + /// Gets or sets a value indicating whether the legend is visible. The titles of the series must be set to use the legend.
117.416 + /// </summary>
117.417 + public bool IsLegendVisible { get; set; }
117.418 +
117.419 + /// <summary>
117.420 + /// Gets the legend area.
117.421 + /// </summary>
117.422 + /// <value> The legend area. </value>
117.423 + public OxyRect LegendArea { get; private set; }
117.424 +
117.425 + /// <summary>
117.426 + /// Gets or sets the background color of the legend. Use null for no background.
117.427 + /// </summary>
117.428 + /// <value> The legend background. </value>
117.429 + public OxyColor LegendBackground { get; set; }
117.430 +
117.431 + /// <summary>
117.432 + /// Gets or sets the border color of the legend.
117.433 + /// </summary>
117.434 + /// <value> The legend border. </value>
117.435 + public OxyColor LegendBorder { get; set; }
117.436 +
117.437 + /// <summary>
117.438 + /// Gets or sets the thickness of the legend border. Use 0 for no border.
117.439 + /// </summary>
117.440 + /// <value> The legend border thickness. </value>
117.441 + public double LegendBorderThickness { get; set; }
117.442 +
117.443 + /// <summary>
117.444 + /// Gets or sets the legend column spacing.
117.445 + /// </summary>
117.446 + /// <value> The legend column spacing. </value>
117.447 + public double LegendColumnSpacing { get; set; }
117.448 +
117.449 + /// <summary>
117.450 + /// Gets or sets the legend font.
117.451 + /// </summary>
117.452 + /// <value> The legend font. </value>
117.453 + public string LegendFont { get; set; }
117.454 +
117.455 + /// <summary>
117.456 + /// Gets or sets the size of the legend font.
117.457 + /// </summary>
117.458 + /// <value> The size of the legend font. </value>
117.459 + public double LegendFontSize { get; set; }
117.460 +
117.461 + /// <summary>
117.462 + /// Gets or sets the color of the legend text.
117.463 + /// </summary>
117.464 + /// <value>
117.465 + /// The color of the legend text.
117.466 + /// </value>
117.467 + /// <remarks>
117.468 + /// If this value is null, the TextColor will be used.
117.469 + /// </remarks>
117.470 + public OxyColor LegendTextColor { get; set; }
117.471 +
117.472 + /// <summary>
117.473 + /// Gets or sets the legend font weight.
117.474 + /// </summary>
117.475 + /// <value> The legend font weight. </value>
117.476 + public double LegendFontWeight { get; set; }
117.477 +
117.478 + /// <summary>
117.479 + /// Gets or sets the legend item alignment.
117.480 + /// </summary>
117.481 + /// <value> The legend item alignment. </value>
117.482 + public HorizontalAlignment LegendItemAlignment { get; set; }
117.483 +
117.484 + /// <summary>
117.485 + /// Gets or sets the legend item order.
117.486 + /// </summary>
117.487 + /// <value> The legend item order. </value>
117.488 + public LegendItemOrder LegendItemOrder { get; set; }
117.489 +
117.490 + /// <summary>
117.491 + /// Gets or sets the legend spacing.
117.492 + /// </summary>
117.493 + /// <value> The legend spacing. </value>
117.494 + public double LegendItemSpacing { get; set; }
117.495 +
117.496 + /// <summary>
117.497 + /// Gets or sets the legend margin.
117.498 + /// </summary>
117.499 + /// <value> The legend margin. </value>
117.500 + public double LegendMargin { get; set; }
117.501 +
117.502 + /// <summary>
117.503 + /// Gets or sets the max width of the legend.
117.504 + /// </summary>
117.505 + /// <value>The max width of the legend.</value>
117.506 + public double LegendMaxWidth { get; set; }
117.507 +
117.508 + /// <summary>
117.509 + /// Gets or sets the legend orientation.
117.510 + /// </summary>
117.511 + /// <value> The legend orientation. </value>
117.512 + public LegendOrientation LegendOrientation { get; set; }
117.513 +
117.514 + /// <summary>
117.515 + /// Gets or sets the legend padding.
117.516 + /// </summary>
117.517 + /// <value> The legend padding. </value>
117.518 + public double LegendPadding { get; set; }
117.519 +
117.520 + /// <summary>
117.521 + /// Gets or sets the legend placement.
117.522 + /// </summary>
117.523 + /// <value> The legend placement. </value>
117.524 + public LegendPlacement LegendPlacement { get; set; }
117.525 +
117.526 + /// <summary>
117.527 + /// Gets or sets the legend position.
117.528 + /// </summary>
117.529 + /// <value> The legend position. </value>
117.530 + public LegendPosition LegendPosition { get; set; }
117.531 +
117.532 + /// <summary>
117.533 + /// Gets or sets the length of the legend symbols (the default value is 16).
117.534 + /// </summary>
117.535 + public double LegendSymbolLength { get; set; }
117.536 +
117.537 + /// <summary>
117.538 + /// Gets or sets the legend symbol margins (distance between the symbol and the text).
117.539 + /// </summary>
117.540 + /// <value> The legend symbol margin. </value>
117.541 + public double LegendSymbolMargin { get; set; }
117.542 +
117.543 + /// <summary>
117.544 + /// Gets or sets the legend symbol placement.
117.545 + /// </summary>
117.546 + /// <value> The legend symbol placement. </value>
117.547 + public LegendSymbolPlacement LegendSymbolPlacement { get; set; }
117.548 +
117.549 + /// <summary>
117.550 + /// Gets or sets the legend title.
117.551 + /// </summary>
117.552 + /// <value> The legend title. </value>
117.553 + public string LegendTitle { get; set; }
117.554 +
117.555 + /// <summary>
117.556 + /// Gets or sets the color of the legend title.
117.557 + /// </summary>
117.558 + /// <value>
117.559 + /// The color of the legend title.
117.560 + /// </value>
117.561 + /// <remarks>
117.562 + /// If this value is null, the TextColor will be used.
117.563 + /// </remarks>
117.564 + public OxyColor LegendTitleColor { get; set; }
117.565 +
117.566 + /// <summary>
117.567 + /// Gets or sets the legend title font.
117.568 + /// </summary>
117.569 + /// <value> The legend title font. </value>
117.570 + public string LegendTitleFont { get; set; }
117.571 +
117.572 + /// <summary>
117.573 + /// Gets or sets the size of the legend title font.
117.574 + /// </summary>
117.575 + /// <value> The size of the legend title font. </value>
117.576 + public double LegendTitleFontSize { get; set; }
117.577 +
117.578 + /// <summary>
117.579 + /// Gets or sets the legend title font weight.
117.580 + /// </summary>
117.581 + /// <value> The legend title font weight. </value>
117.582 + public double LegendTitleFontWeight { get; set; }
117.583 +
117.584 + /// <summary>
117.585 + /// Gets or sets the padding around the plot.
117.586 + /// </summary>
117.587 + /// <value> The padding. </value>
117.588 + public OxyThickness Padding { get; set; }
117.589 +
117.590 + /// <summary>
117.591 + /// Gets the total width of the plot (in device units).
117.592 + /// </summary>
117.593 + public double Width { get; private set; }
117.594 +
117.595 + /// <summary>
117.596 + /// Gets the total height of the plot (in device units).
117.597 + /// </summary>
117.598 + public double Height { get; private set; }
117.599 +
117.600 + /// <summary>
117.601 + /// Gets the area including both the plot and the axes. Outside legends are rendered outside this rectangle.
117.602 + /// </summary>
117.603 + /// <value> The plot and axis area. </value>
117.604 + public OxyRect PlotAndAxisArea { get; private set; }
117.605 +
117.606 + /// <summary>
117.607 + /// Gets the plot area. This area is used to draw the series (not including axes or legends).
117.608 + /// </summary>
117.609 + /// <value> The plot area. </value>
117.610 + public OxyRect PlotArea { get; private set; }
117.611 +
117.612 + /// <summary>
117.613 + /// Gets or sets the distance between two neighbourhood tiers of the same AxisPosition.
117.614 + /// </summary>
117.615 + public double AxisTierDistance { get; set; }
117.616 +
117.617 + /// <summary>
117.618 + /// Gets or sets the color of the background of the plot area.
117.619 + /// </summary>
117.620 + public OxyColor PlotAreaBackground { get; set; }
117.621 +
117.622 + /// <summary>
117.623 + /// Gets or sets the color of the border around the plot area.
117.624 + /// </summary>
117.625 + /// <value> The color of the box. </value>
117.626 + public OxyColor PlotAreaBorderColor { get; set; }
117.627 +
117.628 + /// <summary>
117.629 + /// Gets or sets the thickness of the border around the plot area.
117.630 + /// </summary>
117.631 + /// <value> The box thickness. </value>
117.632 + public double PlotAreaBorderThickness { get; set; }
117.633 +
117.634 + /// <summary>
117.635 + /// Gets or sets the minimum margins around the plot (this should be large enough to fit the axes). The default value is (60, 4, 4, 40). Set AutoAdjustPlotMargins if you want the margins to be adjusted when the axes require more space.
117.636 + /// </summary>
117.637 + public OxyThickness PlotMargins { get; set; }
117.638 +
117.639 + /// <summary>
117.640 + /// Gets or sets the type of the coordinate system.
117.641 + /// </summary>
117.642 + /// <value> The type of the plot. </value>
117.643 + public PlotType PlotType { get; set; }
117.644 +
117.645 + /// <summary>
117.646 + /// Gets or sets the color of the selection.
117.647 + /// </summary>
117.648 + /// <value>
117.649 + /// The color of the selection.
117.650 + /// </value>
117.651 + public OxyColor SelectionColor { get; set; }
117.652 +
117.653 + /// <summary>
117.654 + /// Gets or sets the series.
117.655 + /// </summary>
117.656 + /// <value> The series. </value>
117.657 + public Collection<Series.Series> Series { get; set; }
117.658 +
117.659 + /// <summary>
117.660 + /// Gets or sets the subtitle.
117.661 + /// </summary>
117.662 + /// <value> The subtitle. </value>
117.663 + public string Subtitle { get; set; }
117.664 +
117.665 + /// <summary>
117.666 + /// Gets or sets the subtitle font. If this property is null, the Title font will be used.
117.667 + /// </summary>
117.668 + /// <value> The subtitle font. </value>
117.669 + public string SubtitleFont { get; set; }
117.670 +
117.671 + /// <summary>
117.672 + /// Gets or sets the size of the subtitle font.
117.673 + /// </summary>
117.674 + /// <value> The size of the subtitle font. </value>
117.675 + public double SubtitleFontSize { get; set; }
117.676 +
117.677 + /// <summary>
117.678 + /// Gets or sets the subtitle font weight.
117.679 + /// </summary>
117.680 + /// <value> The subtitle font weight. </value>
117.681 + public double SubtitleFontWeight { get; set; }
117.682 +
117.683 + /// <summary>
117.684 + /// Gets or sets the default color of the text in the plot (titles, legends, annotations, axes).
117.685 + /// </summary>
117.686 + /// <value> The color of the text. </value>
117.687 + public OxyColor TextColor { get; set; }
117.688 +
117.689 + /// <summary>
117.690 + /// Gets or sets the title.
117.691 + /// </summary>
117.692 + /// <value> The title. </value>
117.693 + public string Title { get; set; }
117.694 +
117.695 + /// <summary>
117.696 + /// Gets or sets the color of the title.
117.697 + /// </summary>
117.698 + /// <value>
117.699 + /// The color of the title.
117.700 + /// </value>
117.701 + /// <remarks>
117.702 + /// If the value is null, the TextColor will be used.
117.703 + /// </remarks>
117.704 + public OxyColor TitleColor { get; set; }
117.705 +
117.706 + /// <summary>
117.707 + /// Gets or sets the color of the subtitle.
117.708 + /// </summary>
117.709 + /// <value>
117.710 + /// The color of the subtitle.
117.711 + /// </value>
117.712 + public OxyColor SubtitleColor { get; set; }
117.713 +
117.714 + /// <summary>
117.715 + /// Gets the title area.
117.716 + /// </summary>
117.717 + /// <value> The title area. </value>
117.718 + public OxyRect TitleArea { get; private set; }
117.719 +
117.720 + /// <summary>
117.721 + /// Gets or sets the title font.
117.722 + /// </summary>
117.723 + /// <value> The title font. </value>
117.724 + public string TitleFont { get; set; }
117.725 +
117.726 + /// <summary>
117.727 + /// Gets or sets the size of the title font.
117.728 + /// </summary>
117.729 + /// <value> The size of the title font. </value>
117.730 + public double TitleFontSize { get; set; }
117.731 +
117.732 + /// <summary>
117.733 + /// Gets or sets the title font weight.
117.734 + /// </summary>
117.735 + /// <value> The title font weight. </value>
117.736 + public double TitleFontWeight { get; set; }
117.737 +
117.738 + /// <summary>
117.739 + /// Gets or sets the padding around the title.
117.740 + /// </summary>
117.741 + /// <value> The title padding. </value>
117.742 + public double TitlePadding { get; set; }
117.743 +
117.744 + /// <summary>
117.745 + /// Gets the default angle axis.
117.746 + /// </summary>
117.747 + /// <value> The default angle axis. </value>
117.748 + public AngleAxis DefaultAngleAxis { get; private set; }
117.749 +
117.750 + /// <summary>
117.751 + /// Gets the default magnitude axis.
117.752 + /// </summary>
117.753 + /// <value> The default magnitude axis. </value>
117.754 + public MagnitudeAxis DefaultMagnitudeAxis { get; private set; }
117.755 +
117.756 + /// <summary>
117.757 + /// Gets the default X axis.
117.758 + /// </summary>
117.759 + /// <value> The default X axis. </value>
117.760 + public Axis DefaultXAxis { get; private set; }
117.761 +
117.762 + /// <summary>
117.763 + /// Gets the default Y axis.
117.764 + /// </summary>
117.765 + /// <value> The default Y axis. </value>
117.766 + public Axis DefaultYAxis { get; private set; }
117.767 +
117.768 + /// <summary>
117.769 + /// Gets the default color axis.
117.770 + /// </summary>
117.771 + /// <value> The default color axis. </value>
117.772 + public ColorAxis DefaultColorAxis { get; private set; }
117.773 +
117.774 + /// <summary>
117.775 + /// Gets the actual title font.
117.776 + /// </summary>
117.777 + protected string ActualTitleFont
117.778 + {
117.779 + get
117.780 + {
117.781 + return this.TitleFont ?? this.DefaultFont;
117.782 + }
117.783 + }
117.784 +
117.785 + /// <summary>
117.786 + /// Gets the actual subtitle font.
117.787 + /// </summary>
117.788 + protected string ActualSubtitleFont
117.789 + {
117.790 + get
117.791 + {
117.792 + return this.SubtitleFont ?? this.DefaultFont;
117.793 + }
117.794 + }
117.795 +
117.796 + /// <summary>
117.797 + /// Gets the visible series.
117.798 + /// </summary>
117.799 + /// <value> The visible series. </value>
117.800 + private IEnumerable<Series.Series> VisibleSeries
117.801 + {
117.802 + get
117.803 + {
117.804 + return this.Series.Where(s => s.IsVisible);
117.805 + }
117.806 + }
117.807 +
117.808 + /// <summary>
117.809 + /// Attaches this model to the specified plot control.
117.810 + /// </summary>
117.811 + /// <param name="plotControl">The plot control.</param>
117.812 + /// <remarks>
117.813 + /// Only one plot control can be attached to the plot model.
117.814 + /// The plot model contains data (e.g. axis scaling) that is only relevant to the current plot control.
117.815 + /// </remarks>
117.816 + public void AttachPlotControl(IPlotControl plotControl)
117.817 + {
117.818 + this.PlotControl = plotControl;
117.819 + }
117.820 +
117.821 + /// <summary>
117.822 + /// Creates a report for the plot.
117.823 + /// </summary>
117.824 + /// <returns>
117.825 + /// A report.
117.826 + /// </returns>
117.827 + public Report CreateReport()
117.828 + {
117.829 + var r = new Report { Culture = CultureInfo.InvariantCulture };
117.830 +
117.831 + r.AddHeader(1, "P L O T R E P O R T");
117.832 + r.AddHeader(2, "=== PlotModel ===");
117.833 + r.AddPropertyTable("PlotModel", this);
117.834 +
117.835 + r.AddHeader(2, "=== Axes ===");
117.836 + foreach (Axis a in this.Axes)
117.837 + {
117.838 + r.AddPropertyTable(a.GetType().Name, a);
117.839 + }
117.840 +
117.841 + r.AddHeader(2, "=== Annotations ===");
117.842 + foreach (var a in this.Annotations)
117.843 + {
117.844 + r.AddPropertyTable(a.GetType().Name, a);
117.845 + }
117.846 +
117.847 + r.AddHeader(2, "=== Series ===");
117.848 + foreach (var s in this.Series)
117.849 + {
117.850 + r.AddPropertyTable(s.GetType().Name, s);
117.851 + var ds = s as DataPointSeries;
117.852 + if (ds != null)
117.853 + {
117.854 + var fields = new List<ItemsTableField> { new ItemsTableField("X", "X"), new ItemsTableField("Y", "Y") };
117.855 + r.AddItemsTable("Data", ds.Points, fields);
117.856 + }
117.857 + }
117.858 +
117.859 + var assemblyName = new AssemblyName(Assembly.GetExecutingAssembly().FullName);
117.860 + r.AddParagraph(string.Format("Report generated by OxyPlot {0}", assemblyName.Version.ToString(3)));
117.861 +
117.862 + return r;
117.863 + }
117.864 +
117.865 + /// <summary>
117.866 + /// Creates a text report for the plot.
117.867 + /// </summary>
117.868 + /// <returns>
117.869 + /// The create text report.
117.870 + /// </returns>
117.871 + public string CreateTextReport()
117.872 + {
117.873 + using (var ms = new MemoryStream())
117.874 + {
117.875 + var trw = new TextReportWriter(ms);
117.876 + Report report = this.CreateReport();
117.877 + report.Write(trw);
117.878 + trw.Flush();
117.879 + ms.Position = 0;
117.880 + var r = new StreamReader(ms);
117.881 + return r.ReadToEnd();
117.882 + }
117.883 + }
117.884 +
117.885 + /// <summary>
117.886 + /// Refreshes the plot.
117.887 + /// </summary>
117.888 + /// <param name="updateData">Updates all data sources if set to <c>true</c>.</param>
117.889 + public void RefreshPlot(bool updateData)
117.890 + {
117.891 + if (this.PlotControl == null)
117.892 + {
117.893 + return;
117.894 + }
117.895 +
117.896 + this.PlotControl.RefreshPlot(updateData);
117.897 + }
117.898 +
117.899 + /// <summary>
117.900 + /// Invalidates the plot.
117.901 + /// </summary>
117.902 + /// <param name="updateData">Updates all data sources if set to <c>true</c>.</param>
117.903 + public void InvalidatePlot(bool updateData)
117.904 + {
117.905 + if (this.PlotControl == null)
117.906 + {
117.907 + return;
117.908 + }
117.909 +
117.910 + this.PlotControl.InvalidatePlot(updateData);
117.911 + }
117.912 +
117.913 + /// <summary>
117.914 + /// Gets the first axes that covers the area of the specified point.
117.915 + /// </summary>
117.916 + /// <param name="pt">
117.917 + /// The point.
117.918 + /// </param>
117.919 + /// <param name="xaxis">
117.920 + /// The xaxis.
117.921 + /// </param>
117.922 + /// <param name="yaxis">
117.923 + /// The yaxis.
117.924 + /// </param>
117.925 + public void GetAxesFromPoint(ScreenPoint pt, out Axis xaxis, out Axis yaxis)
117.926 + {
117.927 + xaxis = yaxis = null;
117.928 +
117.929 + // Get the axis position of the given point. Using null if the point is inside the plot area.
117.930 + AxisPosition? position = null;
117.931 + double plotAreaValue = 0;
117.932 + if (pt.X < this.PlotArea.Left)
117.933 + {
117.934 + position = AxisPosition.Left;
117.935 + plotAreaValue = this.PlotArea.Left;
117.936 + }
117.937 +
117.938 + if (pt.X > this.PlotArea.Right)
117.939 + {
117.940 + position = AxisPosition.Right;
117.941 + plotAreaValue = this.PlotArea.Right;
117.942 + }
117.943 +
117.944 + if (pt.Y < this.PlotArea.Top)
117.945 + {
117.946 + position = AxisPosition.Top;
117.947 + plotAreaValue = this.PlotArea.Top;
117.948 + }
117.949 +
117.950 + if (pt.Y > this.PlotArea.Bottom)
117.951 + {
117.952 + position = AxisPosition.Bottom;
117.953 + plotAreaValue = this.PlotArea.Bottom;
117.954 + }
117.955 +
117.956 + foreach (var axis in this.Axes)
117.957 + {
117.958 + if (axis is ColorAxis)
117.959 + {
117.960 + continue;
117.961 + }
117.962 +
117.963 + if (axis is MagnitudeAxis)
117.964 + {
117.965 + xaxis = axis;
117.966 + continue;
117.967 + }
117.968 +
117.969 + if (axis is AngleAxis)
117.970 + {
117.971 + yaxis = axis;
117.972 + continue;
117.973 + }
117.974 +
117.975 + double x = double.NaN;
117.976 + if (axis.IsHorizontal())
117.977 + {
117.978 + x = axis.InverseTransform(pt.X);
117.979 + }
117.980 +
117.981 + if (axis.IsVertical())
117.982 + {
117.983 + x = axis.InverseTransform(pt.Y);
117.984 + }
117.985 +
117.986 + if (x >= axis.ActualMinimum && x <= axis.ActualMaximum)
117.987 + {
117.988 + if (position == null)
117.989 + {
117.990 + if (axis.IsHorizontal())
117.991 + {
117.992 + if (xaxis == null)
117.993 + {
117.994 + xaxis = axis;
117.995 + }
117.996 + }
117.997 + else if (axis.IsVertical())
117.998 + {
117.999 + if (yaxis == null)
117.1000 + {
117.1001 + yaxis = axis;
117.1002 + }
117.1003 + }
117.1004 + }
117.1005 + else if (position == axis.Position)
117.1006 + {
117.1007 + // Choose right tier
117.1008 + double positionTierMinShift = axis.PositionTierMinShift;
117.1009 + double positionTierMaxShift = axis.PositionTierMaxShift;
117.1010 +
117.1011 + double posValue = axis.IsHorizontal() ? pt.Y : pt.X;
117.1012 + bool isLeftOrTop = position == AxisPosition.Top || position == AxisPosition.Left;
117.1013 + if ((posValue >= plotAreaValue + positionTierMinShift
117.1014 + && posValue < plotAreaValue + positionTierMaxShift && !isLeftOrTop)
117.1015 + ||
117.1016 + (posValue <= plotAreaValue - positionTierMinShift
117.1017 + && posValue > plotAreaValue - positionTierMaxShift && isLeftOrTop))
117.1018 + {
117.1019 + if (axis.IsHorizontal())
117.1020 + {
117.1021 + if (xaxis == null)
117.1022 + {
117.1023 + xaxis = axis;
117.1024 + }
117.1025 + }
117.1026 + else if (axis.IsVertical())
117.1027 + {
117.1028 + if (yaxis == null)
117.1029 + {
117.1030 + yaxis = axis;
117.1031 + }
117.1032 + }
117.1033 + }
117.1034 + }
117.1035 + }
117.1036 + }
117.1037 + }
117.1038 +
117.1039 + /// <summary>
117.1040 + /// Gets the default color from the DefaultColors palette.
117.1041 + /// </summary>
117.1042 + /// <returns>
117.1043 + /// The next default color.
117.1044 + /// </returns>
117.1045 + public OxyColor GetDefaultColor()
117.1046 + {
117.1047 + return this.DefaultColors[this.currentColorIndex++ % this.DefaultColors.Count];
117.1048 + }
117.1049 +
117.1050 + /// <summary>
117.1051 + /// Gets the default line style.
117.1052 + /// </summary>
117.1053 + /// <returns>
117.1054 + /// The next default line style.
117.1055 + /// </returns>
117.1056 + public LineStyle GetDefaultLineStyle()
117.1057 + {
117.1058 + return (LineStyle)((this.currentColorIndex / this.DefaultColors.Count) % (int)LineStyle.None);
117.1059 + }
117.1060 +
117.1061 + /// <summary>
117.1062 + /// Gets a series from the specified point.
117.1063 + /// </summary>
117.1064 + /// <param name="point">
117.1065 + /// The point.
117.1066 + /// </param>
117.1067 + /// <param name="limit">
117.1068 + /// The limit.
117.1069 + /// </param>
117.1070 + /// <returns>
117.1071 + /// The nearest series.
117.1072 + /// </returns>
117.1073 + public Series.Series GetSeriesFromPoint(ScreenPoint point, double limit)
117.1074 + {
117.1075 + double mindist = double.MaxValue;
117.1076 + Series.Series closest = null;
117.1077 + foreach (var s in this.VisibleSeries.Reverse())
117.1078 + {
117.1079 + var ts = s as ITrackableSeries;
117.1080 + if (ts == null)
117.1081 + {
117.1082 + continue;
117.1083 + }
117.1084 +
117.1085 + var thr = ts.GetNearestPoint(point, true) ?? ts.GetNearestPoint(point, false);
117.1086 +
117.1087 + if (thr == null)
117.1088 + {
117.1089 + continue;
117.1090 + }
117.1091 +
117.1092 + // find distance to this point on the screen
117.1093 + double dist = point.DistanceTo(thr.Position);
117.1094 + if (dist < mindist)
117.1095 + {
117.1096 + closest = s;
117.1097 + mindist = dist;
117.1098 + }
117.1099 + }
117.1100 +
117.1101 + if (mindist < limit)
117.1102 + {
117.1103 + return closest;
117.1104 + }
117.1105 +
117.1106 + return null;
117.1107 + }
117.1108 +
117.1109 + /// <summary>
117.1110 + /// Generates C# code of the model.
117.1111 + /// </summary>
117.1112 + /// <returns>
117.1113 + /// C# code.
117.1114 + /// </returns>
117.1115 + public string ToCode()
117.1116 + {
117.1117 + var cg = new CodeGenerator(this);
117.1118 + return cg.ToCode();
117.1119 + }
117.1120 +
117.1121 + /// <summary>
117.1122 + /// Returns a <see cref="System.String"/> that represents this instance.
117.1123 + /// </summary>
117.1124 + /// <returns>
117.1125 + /// A <see cref="System.String"/> that represents this instance.
117.1126 + /// </returns>
117.1127 + public override string ToString()
117.1128 + {
117.1129 + return this.Title;
117.1130 + }
117.1131 +
117.1132 + /// <summary>
117.1133 + /// Create an svg model and return it as a string.
117.1134 + /// </summary>
117.1135 + /// <param name="width">The width (points).</param>
117.1136 + /// <param name="height">The height (points).</param>
117.1137 + /// <param name="isDocument">if set to <c>true</c>, the xml headers will be included (?xml and !DOCTYPE).</param>
117.1138 + /// <param name="textMeasurer">The text measurer.</param>
117.1139 + /// <returns>The svg string.</returns>
117.1140 + public string ToSvg(double width, double height, bool isDocument, IRenderContext textMeasurer)
117.1141 + {
117.1142 + return SvgExporter.ExportToString(this, width, height, isDocument, textMeasurer);
117.1143 + }
117.1144 +
117.1145 + /// <summary>
117.1146 + /// Gets all elements of the plot model.
117.1147 + /// </summary>
117.1148 + /// <returns>An enumerator of the plot elements.</returns>
117.1149 + public IEnumerable<PlotElement> GetElements()
117.1150 + {
117.1151 + foreach (var axis in this.Axes)
117.1152 + {
117.1153 + yield return axis;
117.1154 + }
117.1155 +
117.1156 + foreach (var annotation in this.Annotations)
117.1157 + {
117.1158 + yield return annotation;
117.1159 + }
117.1160 +
117.1161 + foreach (var s in this.Series)
117.1162 + {
117.1163 + yield return s;
117.1164 + }
117.1165 + }
117.1166 +
117.1167 + /// <summary>
117.1168 + /// Updates all axes and series. 0. Updates the owner PlotModel of all plot items (axes, series and annotations)
117.1169 + /// 1. Updates the data of each Series (only if updateData==true).
117.1170 + /// 2. Ensure that all series have axes assigned.
117.1171 + /// 3. Updates the max and min of the axes.
117.1172 + /// </summary>
117.1173 + /// <param name="updateData">
117.1174 + /// if set to <c>true</c> , all data collections will be updated.
117.1175 + /// </param>
117.1176 + public void Update(bool updateData = true)
117.1177 + {
117.1178 + lock (this.syncRoot)
117.1179 + {
117.1180 + this.OnUpdating();
117.1181 +
117.1182 + // update the owner PlotModel
117.1183 + foreach (var s in this.VisibleSeries)
117.1184 + {
117.1185 + s.PlotModel = this;
117.1186 + }
117.1187 +
117.1188 + foreach (var a in this.Annotations)
117.1189 + {
117.1190 + a.PlotModel = this;
117.1191 + }
117.1192 +
117.1193 + // Updates the default axes
117.1194 + this.EnsureDefaultAxes();
117.1195 +
117.1196 + // Update data of the series
117.1197 + if (updateData)
117.1198 + {
117.1199 + foreach (var s in this.VisibleSeries)
117.1200 + {
117.1201 + s.UpdateData();
117.1202 + }
117.1203 + }
117.1204 +
117.1205 + foreach (var a in this.Axes)
117.1206 + {
117.1207 + a.PlotModel = this;
117.1208 + }
117.1209 +
117.1210 + foreach (var c in this.Axes.OfType<CategoryAxis>())
117.1211 + {
117.1212 + c.UpdateLabels(this.VisibleSeries);
117.1213 + }
117.1214 +
117.1215 + // Update valid data of the series
117.1216 + if (updateData)
117.1217 + {
117.1218 + foreach (var s in this.VisibleSeries)
117.1219 + {
117.1220 + s.UpdateValidData();
117.1221 + }
117.1222 + }
117.1223 +
117.1224 + // Updates axes with information from the series
117.1225 + // This is used by the category axis that need to know the number of series using the axis.
117.1226 + foreach (var a in this.Axes)
117.1227 + {
117.1228 + a.UpdateFromSeries(this.VisibleSeries);
117.1229 + }
117.1230 +
117.1231 + // Update the max and min of the axes
117.1232 + this.UpdateMaxMin(updateData);
117.1233 + this.OnUpdated();
117.1234 + }
117.1235 + }
117.1236 +
117.1237 + /// <summary>
117.1238 + /// Updates the axis transforms.
117.1239 + /// </summary>
117.1240 + public void UpdateAxisTransforms()
117.1241 + {
117.1242 + // Update the axis transforms
117.1243 + foreach (var a in this.Axes)
117.1244 + {
117.1245 + a.UpdateTransform(this.PlotArea);
117.1246 + }
117.1247 + }
117.1248 +
117.1249 + /// <summary>
117.1250 + /// Gets the axis for the specified key.
117.1251 + /// </summary>
117.1252 + /// <param name="key">The key.</param>
117.1253 + /// <param name="defaultAxis">The default axis.</param>
117.1254 + /// <returns>The axis, or the defaultAxis if the key is not found.</returns>
117.1255 + public Axis GetAxisOrDefault(string key, Axis defaultAxis)
117.1256 + {
117.1257 + if (key != null)
117.1258 + {
117.1259 + return this.Axes.FirstOrDefault(a => a.Key == key) ?? defaultAxis;
117.1260 + }
117.1261 +
117.1262 + return defaultAxis;
117.1263 + }
117.1264 +
117.1265 + /// <summary>
117.1266 + /// Raises the Updated event.
117.1267 + /// </summary>
117.1268 + protected virtual void OnUpdated()
117.1269 + {
117.1270 + var handler = this.Updated;
117.1271 + if (handler != null)
117.1272 + {
117.1273 + var args = new EventArgs();
117.1274 + handler(this, args);
117.1275 + }
117.1276 + }
117.1277 +
117.1278 + /// <summary>
117.1279 + /// Raises the Updating event.
117.1280 + /// </summary>
117.1281 + protected virtual void OnUpdating()
117.1282 + {
117.1283 + var handler = this.Updating;
117.1284 + if (handler != null)
117.1285 + {
117.1286 + var args = new EventArgs();
117.1287 + handler(this, args);
117.1288 + }
117.1289 + }
117.1290 +
117.1291 + /// <summary>
117.1292 + /// Enforces the same scale on all axes.
117.1293 + /// </summary>
117.1294 + private void EnforceCartesianTransforms()
117.1295 + {
117.1296 + // Set the same scaling on all axes
117.1297 + double sharedScale = this.Axes.Min(a => Math.Abs(a.Scale));
117.1298 + foreach (var a in this.Axes)
117.1299 + {
117.1300 + a.Zoom(sharedScale);
117.1301 + }
117.1302 +
117.1303 + sharedScale = this.Axes.Max(a => Math.Abs(a.Scale));
117.1304 + foreach (var a in this.Axes)
117.1305 + {
117.1306 + a.Zoom(sharedScale);
117.1307 + }
117.1308 +
117.1309 + foreach (var a in this.Axes)
117.1310 + {
117.1311 + a.UpdateTransform(this.PlotArea);
117.1312 + }
117.1313 + }
117.1314 +
117.1315 + /// <summary>
117.1316 + /// Updates the intervals (major and minor step values).
117.1317 + /// </summary>
117.1318 + private void UpdateIntervals()
117.1319 + {
117.1320 + // Update the intervals for all axes
117.1321 + foreach (var a in this.Axes)
117.1322 + {
117.1323 + a.UpdateIntervals(this.PlotArea);
117.1324 + }
117.1325 + }
117.1326 +
117.1327 + /// <summary>
117.1328 + /// Finds and sets the default horizontal and vertical axes (the first horizontal/vertical axes in the Axes collection).
117.1329 + /// </summary>
117.1330 + private void EnsureDefaultAxes()
117.1331 + {
117.1332 + this.DefaultXAxis = this.Axes.FirstOrDefault(a => a.IsHorizontal() && a.IsXyAxis());
117.1333 + this.DefaultYAxis = this.Axes.FirstOrDefault(a => a.IsVertical() && a.IsXyAxis());
117.1334 + this.DefaultMagnitudeAxis = this.Axes.FirstOrDefault(a => a is MagnitudeAxis) as MagnitudeAxis;
117.1335 + this.DefaultAngleAxis = this.Axes.FirstOrDefault(a => a is AngleAxis) as AngleAxis;
117.1336 + this.DefaultColorAxis = this.Axes.FirstOrDefault(a => a is ColorAxis) as ColorAxis;
117.1337 +
117.1338 + if (this.DefaultXAxis == null)
117.1339 + {
117.1340 + this.DefaultXAxis = this.DefaultMagnitudeAxis;
117.1341 + }
117.1342 +
117.1343 + if (this.DefaultYAxis == null)
117.1344 + {
117.1345 + this.DefaultYAxis = this.DefaultAngleAxis;
117.1346 + }
117.1347 +
117.1348 + if (this.PlotType == PlotType.Polar)
117.1349 + {
117.1350 + if (this.DefaultXAxis == null)
117.1351 + {
117.1352 + this.DefaultXAxis = this.DefaultMagnitudeAxis = new MagnitudeAxis();
117.1353 + }
117.1354 +
117.1355 + if (this.DefaultYAxis == null)
117.1356 + {
117.1357 + this.DefaultYAxis = this.DefaultAngleAxis = new AngleAxis();
117.1358 + }
117.1359 + }
117.1360 + else
117.1361 + {
117.1362 + bool createdlinearxaxis = false;
117.1363 + bool createdlinearyaxis = false;
117.1364 + if (this.DefaultXAxis == null)
117.1365 + {
117.1366 + if (this.Series.Any(series => series is ColumnSeries))
117.1367 + {
117.1368 + this.DefaultXAxis = new CategoryAxis { Position = AxisPosition.Bottom };
117.1369 + }
117.1370 + else
117.1371 + {
117.1372 + this.DefaultXAxis = new LinearAxis { Position = AxisPosition.Bottom };
117.1373 + createdlinearxaxis = true;
117.1374 + }
117.1375 + }
117.1376 +
117.1377 + if (this.DefaultYAxis == null)
117.1378 + {
117.1379 + if (this.Series.Any(series => series is BarSeries))
117.1380 + {
117.1381 + this.DefaultYAxis = new CategoryAxis { Position = AxisPosition.Left };
117.1382 + }
117.1383 + else
117.1384 + {
117.1385 + this.DefaultYAxis = new LinearAxis { Position = AxisPosition.Left };
117.1386 + createdlinearyaxis = true;
117.1387 + }
117.1388 + }
117.1389 +
117.1390 + if (createdlinearxaxis && this.DefaultYAxis is CategoryAxis)
117.1391 + {
117.1392 + this.DefaultXAxis.MinimumPadding = 0;
117.1393 + }
117.1394 +
117.1395 + if (createdlinearyaxis && this.DefaultXAxis is CategoryAxis)
117.1396 + {
117.1397 + this.DefaultYAxis.MinimumPadding = 0;
117.1398 + }
117.1399 + }
117.1400 +
117.1401 + bool areAxesRequired = false;
117.1402 + foreach (var s in this.VisibleSeries)
117.1403 + {
117.1404 + if (s.AreAxesRequired())
117.1405 + {
117.1406 + areAxesRequired = true;
117.1407 + }
117.1408 + }
117.1409 +
117.1410 + if (areAxesRequired)
117.1411 + {
117.1412 + if (!this.Axes.Contains(this.DefaultXAxis))
117.1413 + {
117.1414 + Debug.Assert(this.DefaultXAxis != null, "Default x-axis not created.");
117.1415 + if (this.DefaultXAxis != null)
117.1416 + {
117.1417 + this.Axes.Add(this.DefaultXAxis);
117.1418 + }
117.1419 + }
117.1420 +
117.1421 + if (!this.Axes.Contains(this.DefaultYAxis))
117.1422 + {
117.1423 + Debug.Assert(this.DefaultYAxis != null, "Default y-axis not created.");
117.1424 + if (this.DefaultYAxis != null)
117.1425 + {
117.1426 + this.Axes.Add(this.DefaultYAxis);
117.1427 + }
117.1428 + }
117.1429 + }
117.1430 +
117.1431 + // Update the x/index axes of series without axes defined
117.1432 + foreach (var s in this.VisibleSeries)
117.1433 + {
117.1434 + if (s.AreAxesRequired())
117.1435 + {
117.1436 + s.EnsureAxes();
117.1437 + }
117.1438 + }
117.1439 +
117.1440 + // Update the x/index axes of annotations without axes defined
117.1441 + foreach (var a in this.Annotations)
117.1442 + {
117.1443 + a.EnsureAxes();
117.1444 + }
117.1445 + }
117.1446 +
117.1447 + /// <summary>
117.1448 + /// Resets the default color index.
117.1449 + /// </summary>
117.1450 + private void ResetDefaultColor()
117.1451 + {
117.1452 + this.currentColorIndex = 0;
117.1453 + }
117.1454 +
117.1455 + /// <summary>
117.1456 + /// Updates maximum and minimum values of the axes from values of all data series.
117.1457 + /// </summary>
117.1458 + /// <param name="isDataUpdated">
117.1459 + /// if set to <c>true</c> , the data has been updated.
117.1460 + /// </param>
117.1461 + private void UpdateMaxMin(bool isDataUpdated)
117.1462 + {
117.1463 + if (isDataUpdated)
117.1464 + {
117.1465 + foreach (var a in this.Axes)
117.1466 + {
117.1467 + a.ResetDataMaxMin();
117.1468 + }
117.1469 +
117.1470 + // data has been updated, so we need to calculate the max/min of the series again
117.1471 + foreach (var s in this.VisibleSeries)
117.1472 + {
117.1473 + s.UpdateMaxMin();
117.1474 + }
117.1475 + }
117.1476 +
117.1477 + foreach (var s in this.VisibleSeries)
117.1478 + {
117.1479 + s.UpdateAxisMaxMin();
117.1480 + }
117.1481 +
117.1482 + foreach (var a in this.Axes)
117.1483 + {
117.1484 + a.UpdateActualMaxMin();
117.1485 + }
117.1486 + }
117.1487 + }
117.1488 +}
117.1489 \ No newline at end of file
118.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
118.2 +++ b/External/OxyPlot/OxyPlot/PlotModel/SelectablePlotElement.cs Sat Jun 08 16:53:22 2013 +0000
118.3 @@ -0,0 +1,159 @@
118.4 +// --------------------------------------------------------------------------------------------------------------------
118.5 +// <copyright file="SelectablePlotElement.cs" company="OxyPlot">
118.6 +// The MIT License (MIT)
118.7 +//
118.8 +// Copyright (c) 2012 Oystein Bjorke
118.9 +//
118.10 +// Permission is hereby granted, free of charge, to any person obtaining a
118.11 +// copy of this software and associated documentation files (the
118.12 +// "Software"), to deal in the Software without restriction, including
118.13 +// without limitation the rights to use, copy, modify, merge, publish,
118.14 +// distribute, sublicense, and/or sell copies of the Software, and to
118.15 +// permit persons to whom the Software is furnished to do so, subject to
118.16 +// the following conditions:
118.17 +//
118.18 +// The above copyright notice and this permission notice shall be included
118.19 +// in all copies or substantial portions of the Software.
118.20 +//
118.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
118.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
118.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
118.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
118.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
118.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
118.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
118.28 +// </copyright>
118.29 +// <summary>
118.30 +// Represents a plot element that supports selection.
118.31 +// </summary>
118.32 +// --------------------------------------------------------------------------------------------------------------------
118.33 +namespace OxyPlot
118.34 +{
118.35 + using System;
118.36 +
118.37 + /// <summary>
118.38 + /// Provides an abstract base class for plot elements that support selection.
118.39 + /// </summary>
118.40 + public abstract class SelectablePlotElement : PlotElement
118.41 + {
118.42 + /// <summary>
118.43 + /// The is selected.
118.44 + /// </summary>
118.45 + private bool isSelected;
118.46 +
118.47 + /// <summary>
118.48 + /// Initializes a new instance of the <see cref="SelectablePlotElement"/> class.
118.49 + /// </summary>
118.50 + protected SelectablePlotElement()
118.51 + {
118.52 + this.Selectable = true;
118.53 + this.IsSelected = false;
118.54 + }
118.55 +
118.56 + /// <summary>
118.57 + /// Occurs when the IsSelected property is changed.
118.58 + /// </summary>
118.59 + public event EventHandler Selected;
118.60 +
118.61 + /// <summary>
118.62 + /// Gets or sets the index of the selected item (or -1 if all items are selected).
118.63 + /// </summary>
118.64 + /// <value>
118.65 + /// The index of the selected.
118.66 + /// </value>
118.67 + public int SelectedIndex { get; set; }
118.68 +
118.69 + /// <summary>
118.70 + /// Gets or sets a value indicating whether this plot element is selected.
118.71 + /// </summary>
118.72 + public bool IsSelected
118.73 + {
118.74 + get
118.75 + {
118.76 + return this.isSelected;
118.77 + }
118.78 +
118.79 + set
118.80 + {
118.81 + if (value == this.isSelected)
118.82 + {
118.83 + return;
118.84 + }
118.85 +
118.86 + this.isSelected = value;
118.87 + this.OnIsSelectedChanged();
118.88 + }
118.89 + }
118.90 +
118.91 + /// <summary>
118.92 + /// Gets or sets a value indicating whether this plot element can be selected.
118.93 + /// </summary>
118.94 + public bool Selectable { get; set; }
118.95 +
118.96 + /// <summary>
118.97 + /// Gets the actual selection color.
118.98 + /// </summary>
118.99 + /// <value> The actual selection color. </value>
118.100 + protected OxyColor ActualSelectedColor
118.101 + {
118.102 + get
118.103 + {
118.104 + if (this.PlotModel != null)
118.105 + {
118.106 + return this.PlotModel.SelectionColor ?? PlotModel.DefaultSelectionColor;
118.107 + }
118.108 +
118.109 + return PlotModel.DefaultSelectionColor;
118.110 + }
118.111 + }
118.112 +
118.113 + /// <summary>
118.114 + /// Gets the selection color it the element is selected, or the specified color if it is not.
118.115 + /// </summary>
118.116 + /// <param name="originalColor">The unselected color of the element.</param>
118.117 + /// <param name="index">The index of the item to check (use -1 for all items).</param>
118.118 + /// <returns>
118.119 + /// A color.
118.120 + /// </returns>
118.121 + protected OxyColor GetSelectableColor(OxyColor originalColor, int index = -1)
118.122 + {
118.123 + if (originalColor == null)
118.124 + {
118.125 + return null;
118.126 + }
118.127 +
118.128 + if (this.IsSelected && (index == -1 || index == this.SelectedIndex))
118.129 + {
118.130 + return this.ActualSelectedColor;
118.131 + }
118.132 +
118.133 + return originalColor;
118.134 + }
118.135 +
118.136 + /// <summary>
118.137 + /// Gets the selection fill color it the element is selected, or the specified fill color if it is not.
118.138 + /// </summary>
118.139 + /// <param name="originalColor">The unselected fill color of the element.</param>
118.140 + /// <param name="index">The index of the item to check (use -1 for all items).</param>
118.141 + /// <returns>
118.142 + /// A fill color.
118.143 + /// </returns>
118.144 + protected OxyColor GetSelectableFillColor(OxyColor originalColor, int index = -1)
118.145 + {
118.146 + return this.GetSelectableColor(originalColor, index);
118.147 + }
118.148 +
118.149 + /// <summary>
118.150 + /// Raises the Selected event.
118.151 + /// </summary>
118.152 + protected void OnIsSelectedChanged()
118.153 + {
118.154 + var eh = this.Selected;
118.155 + if (eh != null)
118.156 + {
118.157 + eh(this, new EventArgs());
118.158 + }
118.159 + }
118.160 +
118.161 + }
118.162 +}
118.163 \ No newline at end of file
119.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
119.2 +++ b/External/OxyPlot/OxyPlot/PlotModel/UIPlotElement.cs Sat Jun 08 16:53:22 2013 +0000
119.3 @@ -0,0 +1,116 @@
119.4 +// --------------------------------------------------------------------------------------------------------------------
119.5 +// <copyright file="UIPlotElement.cs" company="OxyPlot">
119.6 +// The MIT License (MIT)
119.7 +//
119.8 +// Copyright (c) 2012 Oystein Bjorke
119.9 +//
119.10 +// Permission is hereby granted, free of charge, to any person obtaining a
119.11 +// copy of this software and associated documentation files (the
119.12 +// "Software"), to deal in the Software without restriction, including
119.13 +// without limitation the rights to use, copy, modify, merge, publish,
119.14 +// distribute, sublicense, and/or sell copies of the Software, and to
119.15 +// permit persons to whom the Software is furnished to do so, subject to
119.16 +// the following conditions:
119.17 +//
119.18 +// The above copyright notice and this permission notice shall be included
119.19 +// in all copies or substantial portions of the Software.
119.20 +//
119.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
119.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
119.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
119.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
119.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
119.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
119.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
119.28 +// </copyright>
119.29 +// <summary>
119.30 +// Represents a plot element that handles mouse events.
119.31 +// </summary>
119.32 +// --------------------------------------------------------------------------------------------------------------------
119.33 +namespace OxyPlot
119.34 +{
119.35 + using System;
119.36 +
119.37 + /// <summary>
119.38 + /// Provides an abstract base class for plot elements that handle mouse events.
119.39 + /// </summary>
119.40 + public abstract class UIPlotElement : SelectablePlotElement
119.41 + {
119.42 + /// <summary>
119.43 + /// Occurs when a mouse button is pressed down on the model.
119.44 + /// </summary>
119.45 + public event EventHandler<OxyMouseEventArgs> MouseDown;
119.46 +
119.47 + /// <summary>
119.48 + /// Occurs when the mouse is moved on the plot element (only occurs after MouseDown).
119.49 + /// </summary>
119.50 + public event EventHandler<OxyMouseEventArgs> MouseMove;
119.51 +
119.52 + /// <summary>
119.53 + /// Occurs when the mouse button is released on the plot element.
119.54 + /// </summary>
119.55 + public event EventHandler<OxyMouseEventArgs> MouseUp;
119.56 +
119.57 + /// <summary>
119.58 + /// Raises the <see cref="MouseDown"/> event.
119.59 + /// </summary>
119.60 + /// <param name="sender">
119.61 + /// The sender.
119.62 + /// </param>
119.63 + /// <param name="e">
119.64 + /// The <see cref="OxyMouseEventArgs"/> instance containing the event data.
119.65 + /// </param>
119.66 + protected internal virtual void OnMouseDown(object sender, OxyMouseEventArgs e)
119.67 + {
119.68 + if (this.MouseDown != null)
119.69 + {
119.70 + this.MouseDown(sender, e);
119.71 + }
119.72 + }
119.73 +
119.74 + /// <summary>
119.75 + /// Raises the <see cref="MouseMove"/> event.
119.76 + /// </summary>
119.77 + /// <param name="sender">
119.78 + /// The sender.
119.79 + /// </param>
119.80 + /// <param name="e">
119.81 + /// The <see cref="OxyMouseEventArgs"/> instance containing the event data.
119.82 + /// </param>
119.83 + protected internal virtual void OnMouseMove(object sender, OxyMouseEventArgs e)
119.84 + {
119.85 + if (this.MouseMove != null)
119.86 + {
119.87 + this.MouseMove(sender, e);
119.88 + }
119.89 + }
119.90 +
119.91 + /// <summary>
119.92 + /// Raises the <see cref="MouseUp"/> event.
119.93 + /// </summary>
119.94 + /// <param name="sender">
119.95 + /// The sender.
119.96 + /// </param>
119.97 + /// <param name="e">
119.98 + /// The <see cref="OxyMouseEventArgs"/> instance containing the event data.
119.99 + /// </param>
119.100 + protected internal virtual void OnMouseUp(object sender, OxyMouseEventArgs e)
119.101 + {
119.102 + if (this.MouseUp != null)
119.103 + {
119.104 + this.MouseUp(sender, e);
119.105 + }
119.106 + }
119.107 +
119.108 + /// <summary>
119.109 + /// Tests if the plot element is hit by the specified point.
119.110 + /// </summary>
119.111 + /// <param name="point">The point.</param>
119.112 + /// <param name="tolerance">The tolerance.</param>
119.113 + /// <returns>
119.114 + /// A hit test result.
119.115 + /// </returns>
119.116 + protected internal abstract HitTestResult HitTest(ScreenPoint point, double tolerance);
119.117 +
119.118 + }
119.119 +}
119.120 \ No newline at end of file
120.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
120.2 +++ b/External/OxyPlot/OxyPlot/Properties/AssemblyInfo.cs Sat Jun 08 16:53:22 2013 +0000
120.3 @@ -0,0 +1,10 @@
120.4 +// --------------------------------------------------------------------------------------------------------------------
120.5 +// <copyright file="AssemblyInfo.cs" company="OxyPlot">
120.6 +// http://oxyplot.codeplex.com, license: MIT
120.7 +// </copyright>
120.8 +// --------------------------------------------------------------------------------------------------------------------
120.9 +
120.10 +using System.Reflection;
120.11 +
120.12 +[assembly: AssemblyTitle("OxyPlot")]
120.13 +[assembly: AssemblyDescription("OxyPlot core library")]
120.14 \ No newline at end of file
121.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
121.2 +++ b/External/OxyPlot/OxyPlot/Render/AngleAxisRenderer.cs Sat Jun 08 16:53:22 2013 +0000
121.3 @@ -0,0 +1,166 @@
121.4 +// --------------------------------------------------------------------------------------------------------------------
121.5 +// <copyright file="AngleAxisRenderer.cs" company="OxyPlot">
121.6 +// The MIT License (MIT)
121.7 +//
121.8 +// Copyright (c) 2012 Oystein Bjorke
121.9 +//
121.10 +// Permission is hereby granted, free of charge, to any person obtaining a
121.11 +// copy of this software and associated documentation files (the
121.12 +// "Software"), to deal in the Software without restriction, including
121.13 +// without limitation the rights to use, copy, modify, merge, publish,
121.14 +// distribute, sublicense, and/or sell copies of the Software, and to
121.15 +// permit persons to whom the Software is furnished to do so, subject to
121.16 +// the following conditions:
121.17 +//
121.18 +// The above copyright notice and this permission notice shall be included
121.19 +// in all copies or substantial portions of the Software.
121.20 +//
121.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
121.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
121.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
121.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
121.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
121.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
121.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
121.28 +// </copyright>
121.29 +// <summary>
121.30 +// The angle axis renderer.
121.31 +// </summary>
121.32 +// --------------------------------------------------------------------------------------------------------------------
121.33 +namespace OxyPlot
121.34 +{
121.35 + using System;
121.36 +
121.37 + using OxyPlot.Axes;
121.38 +
121.39 + /// <summary>
121.40 + /// Provides functionality to render <see cref="AngleAxis"/>.
121.41 + /// </summary>
121.42 + public class AngleAxisRenderer : AxisRendererBase
121.43 + {
121.44 + /// <summary>
121.45 + /// Initializes a new instance of the <see cref="AngleAxisRenderer"/> class.
121.46 + /// </summary>
121.47 + /// <param name="rc">
121.48 + /// The render context.
121.49 + /// </param>
121.50 + /// <param name="plot">
121.51 + /// The plot.
121.52 + /// </param>
121.53 + public AngleAxisRenderer(IRenderContext rc, PlotModel plot)
121.54 + : base(rc, plot)
121.55 + {
121.56 + }
121.57 +
121.58 + /// <summary>
121.59 + /// Renders the specified axis.
121.60 + /// </summary>
121.61 + /// <param name="axis">The axis.</param>
121.62 + /// <param name="pass">The render pass.</param>
121.63 + /// <exception cref="System.InvalidOperationException">Magnitude axis not defined.</exception>
121.64 + public override void Render(Axis axis, int pass)
121.65 + {
121.66 + base.Render(axis, pass);
121.67 +
121.68 + var magnitudeAxis = this.Plot.DefaultMagnitudeAxis;
121.69 +
121.70 + if (axis.RelatedAxis != null)
121.71 + {
121.72 + magnitudeAxis = axis.RelatedAxis as MagnitudeAxis;
121.73 + }
121.74 +
121.75 + if (magnitudeAxis == null)
121.76 + {
121.77 + throw new InvalidOperationException("Magnitude axis not defined.");
121.78 + }
121.79 +
121.80 + double eps = axis.MinorStep * 1e-3;
121.81 +
121.82 + if (axis.ShowMinorTicks)
121.83 + {
121.84 + foreach (double value in this.MinorTickValues)
121.85 + {
121.86 + if (value < axis.ActualMinimum - eps || value > axis.ActualMaximum + eps)
121.87 + {
121.88 + continue;
121.89 + }
121.90 +
121.91 + if (this.MajorTickValues.Contains(value))
121.92 + {
121.93 + continue;
121.94 + }
121.95 +
121.96 + var pt = magnitudeAxis.Transform(magnitudeAxis.ActualMaximum, value, axis);
121.97 +
121.98 + if (this.MinorPen != null)
121.99 + {
121.100 + this.rc.DrawLine(magnitudeAxis.MidPoint.x, magnitudeAxis.MidPoint.y, pt.x, pt.y, this.MinorPen, false);
121.101 + }
121.102 + }
121.103 + }
121.104 +
121.105 + var angleAxis = (AngleAxis)axis;
121.106 + bool isFullCircle = Math.Abs(Math.Abs(angleAxis.EndAngle - angleAxis.StartAngle) - 360) < 1e-6;
121.107 +
121.108 + foreach (double value in this.MajorTickValues)
121.109 + {
121.110 + // skip the last value (overlapping with the first)
121.111 + if (isFullCircle && value > axis.ActualMaximum - eps)
121.112 + {
121.113 + continue;
121.114 + }
121.115 +
121.116 + if (value < axis.ActualMinimum - eps || value > axis.ActualMaximum + eps)
121.117 + {
121.118 + continue;
121.119 + }
121.120 +
121.121 + ScreenPoint pt = magnitudeAxis.Transform(magnitudeAxis.ActualMaximum, value, axis);
121.122 + if (this.MajorPen != null)
121.123 + {
121.124 + this.rc.DrawLine(
121.125 + magnitudeAxis.MidPoint.x, magnitudeAxis.MidPoint.y, pt.x, pt.y, this.MajorPen, false);
121.126 + }
121.127 + }
121.128 +
121.129 + foreach (double value in this.MajorLabelValues)
121.130 + {
121.131 + // skip the last value (overlapping with the first)
121.132 + if (isFullCircle && value > axis.ActualMaximum - eps)
121.133 + {
121.134 + continue;
121.135 + }
121.136 +
121.137 + var pt = magnitudeAxis.Transform(magnitudeAxis.ActualMaximum, value, axis);
121.138 + double angle = Math.Atan2(pt.y - magnitudeAxis.MidPoint.y, pt.x - magnitudeAxis.MidPoint.x);
121.139 +
121.140 + // add some margin
121.141 + pt.x += Math.Cos(angle) * axis.AxisTickToLabelDistance;
121.142 + pt.y += Math.Sin(angle) * axis.AxisTickToLabelDistance;
121.143 +
121.144 + // Convert to degrees
121.145 + angle *= 180 / Math.PI;
121.146 +
121.147 + string text = axis.FormatValue(value);
121.148 +
121.149 + var ha = HorizontalAlignment.Left;
121.150 + var va = VerticalAlignment.Middle;
121.151 +
121.152 + if (Math.Abs(Math.Abs(angle) - 90) < 10)
121.153 + {
121.154 + ha = HorizontalAlignment.Center;
121.155 + va = angle > 90 ? VerticalAlignment.Top : VerticalAlignment.Bottom;
121.156 + angle = 0;
121.157 + }
121.158 + else if (angle > 90 || angle < -90)
121.159 + {
121.160 + angle -= 180;
121.161 + ha = HorizontalAlignment.Right;
121.162 + }
121.163 +
121.164 + this.rc.DrawMathText(
121.165 + pt, text, axis.ActualTextColor, axis.ActualFont, axis.ActualFontSize, axis.ActualFontWeight, angle, ha, va);
121.166 + }
121.167 + }
121.168 + }
121.169 +}
121.170 \ No newline at end of file
122.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
122.2 +++ b/External/OxyPlot/OxyPlot/Render/AxisRenderer.cs Sat Jun 08 16:53:22 2013 +0000
122.3 @@ -0,0 +1,532 @@
122.4 +// --------------------------------------------------------------------------------------------------------------------
122.5 +// <copyright file="AxisRenderer.cs" company="OxyPlot">
122.6 +// The MIT License (MIT)
122.7 +//
122.8 +// Copyright (c) 2012 Oystein Bjorke
122.9 +//
122.10 +// Permission is hereby granted, free of charge, to any person obtaining a
122.11 +// copy of this software and associated documentation files (the
122.12 +// "Software"), to deal in the Software without restriction, including
122.13 +// without limitation the rights to use, copy, modify, merge, publish,
122.14 +// distribute, sublicense, and/or sell copies of the Software, and to
122.15 +// permit persons to whom the Software is furnished to do so, subject to
122.16 +// the following conditions:
122.17 +//
122.18 +// The above copyright notice and this permission notice shall be included
122.19 +// in all copies or substantial portions of the Software.
122.20 +//
122.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
122.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
122.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
122.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
122.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
122.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
122.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
122.28 +// </copyright>
122.29 +// --------------------------------------------------------------------------------------------------------------------
122.30 +using System;
122.31 +using System.Collections.Generic;
122.32 +
122.33 +namespace OxyPlot
122.34 +{
122.35 + public class AxisRenderer
122.36 + {
122.37 + private const double AXIS_LEGEND_DIST = 4; // distance from axis number to axis legend
122.38 + private const double TICK_DIST = 8; // distance from axis tick to number
122.39 +
122.40 + private OxyPen extraPen;
122.41 + private OxyPen majorPen;
122.42 + private OxyPen majorTickPen;
122.43 +
122.44 + private ICollection<double> majorTickValues;
122.45 + private OxyPen minorPen;
122.46 + private OxyPen minorTickPen;
122.47 + private ICollection<double> minorTickValues;
122.48 + private OxyPen zeroPen;
122.49 +
122.50 + protected readonly PlotModel Plot;
122.51 + protected readonly IRenderContext rc;
122.52 +
122.53 + public AxisRenderer(IRenderContext rc, PlotModel plot)
122.54 + {
122.55 + this.Plot = plot;
122.56 + this.rc = rc;
122.57 + }
122.58 +
122.59 + public void Render(Axis axis)
122.60 + {
122.61 + if (axis == null)
122.62 + return;
122.63 +
122.64 + axis.GetTickValues(out majorTickValues, out minorTickValues);
122.65 +
122.66 + CreatePens(axis);
122.67 +
122.68 + if (axis.IsHorizontal())
122.69 + {
122.70 + RenderHorizontalAxis(axis, Plot.DefaultYAxis);
122.71 + }
122.72 + if (axis.IsVertical())
122.73 + {
122.74 + RenderVerticalAxis(axis, Plot.DefaultXAxis);
122.75 + }
122.76 + if (axis.Position == AxisPosition.Angle)
122.77 + {
122.78 + RenderAngleAxis(axis, Plot.DefaultMagnitudeAxis);
122.79 + }
122.80 + if (axis.Position == AxisPosition.Magnitude)
122.81 + {
122.82 + RenderMagnitudeAxis(axis, Plot.DefaultAngleAxis);
122.83 + }
122.84 + }
122.85 +
122.86 + private void RenderMagnitudeAxis(Axis axis, Axis angleAxis)
122.87 + {
122.88 + if (axis.RelatedAxis != null)
122.89 + angleAxis = axis.RelatedAxis;
122.90 +
122.91 + if (axis.ShowMinorTicks)
122.92 + {
122.93 + // GetVerticalTickPositions(axis, axis.TickStyle, axis.MinorTickSize, out y0, out y1);
122.94 +
122.95 + foreach (double xValue in minorTickValues)
122.96 + {
122.97 + if (xValue < axis.ActualMinimum || xValue > axis.ActualMaximum)
122.98 + {
122.99 + continue;
122.100 + }
122.101 +
122.102 + if (majorTickValues.Contains(xValue))
122.103 + {
122.104 + continue;
122.105 + }
122.106 +
122.107 + var pts = new List<ScreenPoint>();
122.108 + for (double th = angleAxis.ActualMinimum;
122.109 + th <= angleAxis.ActualMaximum;
122.110 + th += angleAxis.MinorStep*0.1)
122.111 + {
122.112 + pts.Add(axis.Transform(xValue, th, angleAxis));
122.113 + }
122.114 +
122.115 + if (minorPen != null)
122.116 + {
122.117 + rc.DrawLine(pts, minorPen.Color, minorPen.Thickness, minorPen.DashArray);
122.118 + }
122.119 + // RenderGridline(x, y + y0, x, y + y1, minorTickPen);
122.120 + }
122.121 + }
122.122 +
122.123 + // GetVerticalTickPositions(axis, axis.TickStyle, axis.MajorTickSize, out y0, out y1);
122.124 +
122.125 + foreach (double xValue in majorTickValues)
122.126 + {
122.127 + if (xValue < axis.ActualMinimum || xValue > axis.ActualMaximum)
122.128 + {
122.129 + continue;
122.130 + }
122.131 +
122.132 + var pts = new List<ScreenPoint>();
122.133 + for (double th = angleAxis.ActualMinimum; th <= angleAxis.ActualMaximum; th += angleAxis.MinorStep*0.1)
122.134 + {
122.135 + pts.Add(axis.Transform(xValue, th, angleAxis));
122.136 + }
122.137 +
122.138 + if (majorPen != null)
122.139 + {
122.140 + rc.DrawLine(pts, majorPen.Color, majorPen.Thickness, majorPen.DashArray);
122.141 + }
122.142 +
122.143 + // RenderGridline(x, y + y0, x, y + y1, majorTickPen);
122.144 +
122.145 + //var pt = new ScreenPoint(x, istop ? y + y1 - TICK_DIST : y + y1 + TICK_DIST);
122.146 + //string text = axis.FormatValue(xValue);
122.147 + //double h = rc.MeasureText(text, axis.FontFamily, axis.FontSize, axis.FontWeight).Height;
122.148 +
122.149 + //rc.DrawText(pt, text, plot.TextColor,
122.150 + // axis.FontFamily, axis.FontSize, axis.FontWeight,
122.151 + // axis.Angle,
122.152 + // HorizontalTextAlign.Center, istop ? VerticalTextAlign.Bottom : VerticalTextAlign.Top);
122.153 +
122.154 + //maxh = Math.Max(maxh, h);
122.155 + }
122.156 + }
122.157 +
122.158 + private void RenderAngleAxis(Axis axis, Axis magnitudeAxis)
122.159 + {
122.160 + if (axis.RelatedAxis != null)
122.161 + magnitudeAxis = axis.RelatedAxis;
122.162 +
122.163 + if (axis.ShowMinorTicks)
122.164 + {
122.165 + // GetVerticalTickPositions(axis, axis.TickStyle, axis.MinorTickSize, out y0, out y1);
122.166 +
122.167 + foreach (double xValue in minorTickValues)
122.168 + {
122.169 + if (xValue < axis.ActualMinimum || xValue > axis.ActualMaximum)
122.170 + {
122.171 + continue;
122.172 + }
122.173 +
122.174 + if (majorTickValues.Contains(xValue))
122.175 + {
122.176 + continue;
122.177 + }
122.178 +
122.179 + var pt = magnitudeAxis.Transform(magnitudeAxis.ActualMaximum, xValue, axis);
122.180 +
122.181 + if (minorPen != null)
122.182 + {
122.183 + RenderLine(axis.MidPoint.x, axis.MidPoint.y, pt.x, pt.y, minorPen, false);
122.184 + }
122.185 + // RenderGridline(x, y + y0, x, y + y1, minorTickPen);
122.186 + }
122.187 + }
122.188 +
122.189 + // GetVerticalTickPositions(axis, axis.TickStyle, axis.MajorTickSize, out y0, out y1);
122.190 +
122.191 + foreach (double xValue in majorTickValues)
122.192 + {
122.193 + if (xValue < axis.ActualMinimum || xValue > axis.ActualMaximum)
122.194 + {
122.195 + continue;
122.196 + }
122.197 +
122.198 + var pt = magnitudeAxis.Transform(magnitudeAxis.ActualMaximum, xValue, axis);
122.199 +
122.200 + if (majorPen != null)
122.201 + {
122.202 + RenderLine(axis.MidPoint.x, axis.MidPoint.y, pt.x, pt.y, majorPen, false);
122.203 + }
122.204 + // RenderGridline(x, y + y0, x, y + y1, majorTickPen);
122.205 +
122.206 + //var pt = new ScreenPoint(x, istop ? y + y1 - TICK_DIST : y + y1 + TICK_DIST);
122.207 + //string text = axis.FormatValue(xValue);
122.208 + //double h = rc.MeasureText(text, axis.FontFamily, axis.FontSize, axis.FontWeight).Height;
122.209 +
122.210 + //rc.DrawText(pt, text, plot.TextColor,
122.211 + // axis.FontFamily, axis.FontSize, axis.FontWeight,
122.212 + // axis.Angle,
122.213 + // HorizontalTextAlign.Center, istop ? VerticalTextAlign.Bottom : VerticalTextAlign.Top);
122.214 +
122.215 + //maxh = Math.Max(maxh, h);
122.216 + }
122.217 + }
122.218 +
122.219 + private void RenderLine(double x0, double y0, double x1, double y1, OxyPen pen, bool aliased = true)
122.220 + {
122.221 + if (pen == null)
122.222 + return;
122.223 +
122.224 + rc.DrawLine(new[]
122.225 + {
122.226 + new ScreenPoint(x0, y0),
122.227 + new ScreenPoint(x1, y1)
122.228 + }, pen.Color, pen.Thickness, pen.DashArray, aliased);
122.229 + }
122.230 +
122.231 + private void GetVerticalTickPositions(Axis axis, TickStyle glt, double ticksize,
122.232 + out double y0, out double y1)
122.233 + {
122.234 + y0 = 0;
122.235 + y1 = 0;
122.236 + bool istop = axis.Position == AxisPosition.Top;
122.237 + double topsign = istop ? -1 : 1;
122.238 + switch (glt)
122.239 + {
122.240 + case TickStyle.Crossing:
122.241 + y0 = -ticksize*topsign;
122.242 + y1 = ticksize*topsign;
122.243 + break;
122.244 + case TickStyle.Inside:
122.245 + y0 = -ticksize*topsign;
122.246 + break;
122.247 + case TickStyle.Outside:
122.248 + y1 = ticksize*topsign;
122.249 + break;
122.250 + }
122.251 + }
122.252 +
122.253 + private void GetHorizontalTickPositions(Axis axis, TickStyle glt, double ticksize, out double x0,
122.254 + out double x1)
122.255 + {
122.256 + x0 = 0;
122.257 + x1 = 0;
122.258 + bool isLeft = axis.Position == AxisPosition.Left;
122.259 + double leftSign = isLeft ? -1 : 1;
122.260 + switch (glt)
122.261 + {
122.262 + case TickStyle.Crossing:
122.263 + x0 = -ticksize*leftSign;
122.264 + x1 = ticksize*leftSign;
122.265 + break;
122.266 + case TickStyle.Inside:
122.267 + x0 = -ticksize*leftSign;
122.268 + break;
122.269 + case TickStyle.Outside:
122.270 + x1 = ticksize*leftSign;
122.271 + break;
122.272 + }
122.273 + }
122.274 +
122.275 + public void CreatePens(Axis axis)
122.276 + {
122.277 + minorPen = CreatePen(axis.MinorGridlineColor, axis.MinorGridlineThickness, axis.MinorGridlineStyle);
122.278 + majorPen = CreatePen(axis.MajorGridlineColor, axis.MajorGridlineThickness, axis.MajorGridlineStyle);
122.279 + minorTickPen = CreatePen(axis.TicklineColor, axis.MinorGridlineThickness, LineStyle.Solid);
122.280 + majorTickPen = CreatePen(axis.TicklineColor, axis.MajorGridlineThickness, LineStyle.Solid);
122.281 + zeroPen = CreatePen(axis.MajorGridlineColor, axis.MajorGridlineThickness, axis.MajorGridlineStyle);
122.282 + extraPen = CreatePen(axis.ExtraGridlineColor, axis.ExtraGridlineThickness, axis.ExtraGridlineStyle);
122.283 + }
122.284 +
122.285 + private void RenderHorizontalAxis(Axis axis, Axis perpendicularAxis)
122.286 + {
122.287 + double y = Plot.Bounds.Bottom;
122.288 + switch (axis.Position)
122.289 + {
122.290 + case AxisPosition.Top:
122.291 + y = Plot.Bounds.Top;
122.292 + break;
122.293 + case AxisPosition.Bottom:
122.294 + y = Plot.Bounds.Bottom;
122.295 + break;
122.296 + }
122.297 + if (axis.PositionAtZeroCrossing)
122.298 + {
122.299 + y = perpendicularAxis.TransformX(0);
122.300 + }
122.301 +
122.302 + double y0, y1;
122.303 +
122.304 + if (axis.ShowMinorTicks)
122.305 + {
122.306 + GetVerticalTickPositions(axis, axis.TickStyle, axis.MinorTickSize, out y0, out y1);
122.307 +
122.308 + foreach (double xValue in minorTickValues)
122.309 + {
122.310 + if (xValue < axis.ActualMinimum || xValue > axis.ActualMaximum)
122.311 + {
122.312 + continue;
122.313 + }
122.314 +
122.315 + if (majorTickValues.Contains(xValue))
122.316 + {
122.317 + continue;
122.318 + }
122.319 +
122.320 + double x = axis.TransformX(xValue);
122.321 + if (minorPen != null)
122.322 + {
122.323 + RenderLine(x, Plot.Bounds.Top, x, Plot.Bounds.Bottom, minorPen);
122.324 + }
122.325 + RenderLine(x, y + y0, x, y + y1, minorTickPen);
122.326 + }
122.327 + }
122.328 +
122.329 + GetVerticalTickPositions(axis, axis.TickStyle, axis.MajorTickSize, out y0, out y1);
122.330 +
122.331 + double maxh = 0;
122.332 + bool istop = axis.Position == AxisPosition.Top;
122.333 + foreach (double xValue in majorTickValues)
122.334 + {
122.335 + if (xValue < axis.ActualMinimum || xValue > axis.ActualMaximum)
122.336 + {
122.337 + continue;
122.338 + }
122.339 +
122.340 + double x = axis.TransformX(xValue);
122.341 +
122.342 + if (majorPen != null)
122.343 + {
122.344 + RenderLine(x, Plot.Bounds.Top, x, Plot.Bounds.Bottom, majorPen);
122.345 + }
122.346 + RenderLine(x, y + y0, x, y + y1, majorTickPen);
122.347 +
122.348 + if (xValue == 0 && axis.PositionAtZeroCrossing)
122.349 + continue;
122.350 +
122.351 + var pt = new ScreenPoint(x, istop ? y + y1 - TICK_DIST : y + y1 + TICK_DIST);
122.352 + string text = axis.FormatValue(xValue);
122.353 + double h = rc.MeasureText(text, axis.FontFamily, axis.FontSize, axis.FontWeight).Height;
122.354 +
122.355 + rc.DrawText(pt, text, Plot.TextColor,
122.356 + axis.FontFamily, axis.FontSize, axis.FontWeight,
122.357 + axis.Angle,
122.358 + HorizontalTextAlign.Center, istop ? VerticalTextAlign.Bottom : VerticalTextAlign.Top);
122.359 +
122.360 + maxh = Math.Max(maxh, h);
122.361 + }
122.362 +
122.363 + if (axis.PositionAtZeroCrossing)
122.364 + {
122.365 + double x = axis.TransformX(0);
122.366 + RenderLine(x, Plot.Bounds.Top, x, Plot.Bounds.Bottom, zeroPen);
122.367 + }
122.368 +
122.369 + if (axis.ExtraGridlines != null)
122.370 + {
122.371 + foreach (double x in axis.ExtraGridlines)
122.372 + {
122.373 + if (!IsWithin(x, axis.ActualMinimum, axis.ActualMaximum))
122.374 + continue;
122.375 + double sx = axis.TransformX(x);
122.376 + RenderLine(sx, Plot.Bounds.Top, sx, Plot.Bounds.Bottom, extraPen);
122.377 + }
122.378 + }
122.379 +
122.380 + // The horizontal axis line
122.381 + RenderLine(Plot.Bounds.Left, y, Plot.Bounds.Right, y, majorPen);
122.382 +
122.383 + // The horizontal axis legend (centered horizontally)
122.384 + double legendX = axis.TransformX((axis.ActualMinimum + axis.ActualMaximum)/2);
122.385 + HorizontalTextAlign halign = HorizontalTextAlign.Center;
122.386 + VerticalTextAlign valign = VerticalTextAlign.Bottom;
122.387 +
122.388 + if (axis.PositionAtZeroCrossing)
122.389 + {
122.390 + legendX = perpendicularAxis.TransformX(perpendicularAxis.ActualMaximum);
122.391 + }
122.392 +
122.393 + double legendY = rc.Height - AXIS_LEGEND_DIST;
122.394 + if (istop)
122.395 + {
122.396 + legendY = AXIS_LEGEND_DIST;
122.397 + valign = VerticalTextAlign.Top;
122.398 + }
122.399 + rc.DrawText(new ScreenPoint(legendX, legendY),
122.400 + axis.Title, Plot.TextColor,
122.401 + axis.FontFamily, axis.FontSize, axis.FontWeight, 0, halign, valign);
122.402 + }
122.403 +
122.404 + private OxyPen CreatePen(OxyColor c, double th, LineStyle ls)
122.405 + {
122.406 + if (ls == LineStyle.None || th == 0)
122.407 + return null;
122.408 + return new OxyPen(c, th, ls);
122.409 + }
122.410 +
122.411 + private void RenderVerticalAxis(Axis axis, Axis perpendicularAxis)
122.412 + {
122.413 + double x = Plot.Bounds.Left;
122.414 + switch (axis.Position)
122.415 + {
122.416 + case AxisPosition.Left:
122.417 + x = Plot.Bounds.Left;
122.418 + break;
122.419 + case AxisPosition.Right:
122.420 + x = Plot.Bounds.Right;
122.421 + break;
122.422 + }
122.423 + if (axis.PositionAtZeroCrossing)
122.424 + x = perpendicularAxis.TransformX(0);
122.425 +
122.426 + double x0, x1;
122.427 +
122.428 + if (axis.ShowMinorTicks)
122.429 + {
122.430 + GetHorizontalTickPositions(axis, axis.TickStyle, axis.MinorTickSize, out x0, out x1);
122.431 + foreach (double yValue in minorTickValues)
122.432 + {
122.433 + if (yValue < axis.ActualMinimum || yValue > axis.ActualMaximum)
122.434 + {
122.435 + continue;
122.436 + }
122.437 +
122.438 + if (majorTickValues.Contains(yValue))
122.439 + {
122.440 + continue;
122.441 + }
122.442 + double y = axis.TransformX(yValue);
122.443 +
122.444 + if (minorPen != null)
122.445 + {
122.446 + RenderLine(Plot.Bounds.Left, y, Plot.Bounds.Right, y, minorPen);
122.447 + }
122.448 +
122.449 + RenderLine(x + x0, y, x + x1, y, minorTickPen);
122.450 + }
122.451 + }
122.452 +
122.453 + GetHorizontalTickPositions(axis, axis.TickStyle, axis.MajorTickSize, out x0, out x1);
122.454 + double maxw = 0;
122.455 +
122.456 + bool isleft = axis.Position == AxisPosition.Left;
122.457 +
122.458 + foreach (double yValue in majorTickValues)
122.459 + {
122.460 + if (yValue < axis.ActualMinimum || yValue > axis.ActualMaximum)
122.461 + continue;
122.462 +
122.463 + double y = axis.TransformX(yValue);
122.464 +
122.465 + if (majorPen != null)
122.466 + {
122.467 + RenderLine(Plot.Bounds.Left, y, Plot.Bounds.Right, y, majorPen);
122.468 + }
122.469 +
122.470 + RenderLine(x + x0, y, x + x1, y, majorTickPen);
122.471 +
122.472 + if (yValue == 0 && axis.PositionAtZeroCrossing)
122.473 + continue;
122.474 +
122.475 + var pt = new ScreenPoint(isleft ? x + x1 - TICK_DIST : x + x1 + TICK_DIST, y);
122.476 + string text = axis.FormatValue(yValue);
122.477 + double w = rc.MeasureText(text, axis.FontFamily, axis.FontSize, axis.FontWeight).Height;
122.478 + rc.DrawText(pt, text, Plot.TextColor,
122.479 + axis.FontFamily, axis.FontSize, axis.FontWeight,
122.480 + axis.Angle,
122.481 + isleft ? HorizontalTextAlign.Right : HorizontalTextAlign.Left, VerticalTextAlign.Middle);
122.482 + maxw = Math.Max(maxw, w);
122.483 + }
122.484 +
122.485 + if (axis.PositionAtZeroCrossing)
122.486 + {
122.487 + double y = axis.TransformX(0);
122.488 + RenderLine(Plot.Bounds.Left, y, Plot.Bounds.Right, y, zeroPen);
122.489 + }
122.490 +
122.491 + if (axis.ExtraGridlines != null)
122.492 + foreach (double y in axis.ExtraGridlines)
122.493 + {
122.494 + if (!IsWithin(y, axis.ActualMinimum, axis.ActualMaximum))
122.495 + continue;
122.496 + double sy = axis.TransformX(y);
122.497 + RenderLine(Plot.Bounds.Left, sy, Plot.Bounds.Right, sy, extraPen);
122.498 + }
122.499 +
122.500 + RenderLine(x, Plot.Bounds.Top, x, Plot.Bounds.Bottom, majorPen);
122.501 +
122.502 + double ymid = axis.TransformX((axis.ActualMinimum + axis.ActualMaximum)/2);
122.503 +
122.504 + HorizontalTextAlign halign = HorizontalTextAlign.Center;
122.505 + VerticalTextAlign valign = VerticalTextAlign.Top;
122.506 +
122.507 + if (axis.PositionAtZeroCrossing)
122.508 + {
122.509 + ymid = perpendicularAxis.TransformX(perpendicularAxis.ActualMaximum);
122.510 + // valign = axis.IsReversed ? VerticalTextAlign.Top : VerticalTextAlign.Bottom;
122.511 + }
122.512 +
122.513 + if (isleft)
122.514 + {
122.515 + x = AXIS_LEGEND_DIST;
122.516 + }
122.517 + else
122.518 + {
122.519 + x = rc.Width - AXIS_LEGEND_DIST;
122.520 + valign = VerticalTextAlign.Bottom;
122.521 + }
122.522 +
122.523 + rc.DrawText(new ScreenPoint(x, ymid), axis.Title, Plot.TextColor,
122.524 + axis.FontFamily, axis.FontSize, axis.FontWeight,
122.525 + -90, halign, valign);
122.526 + }
122.527 +
122.528 + private bool IsWithin(double d, double min, double max)
122.529 + {
122.530 + if (d < min) return false;
122.531 + if (d > max) return false;
122.532 + return true;
122.533 + }
122.534 + }
122.535 +}
122.536 \ No newline at end of file
123.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
123.2 +++ b/External/OxyPlot/OxyPlot/Render/AxisRendererBase.cs Sat Jun 08 16:53:22 2013 +0000
123.3 @@ -0,0 +1,217 @@
123.4 +// --------------------------------------------------------------------------------------------------------------------
123.5 +// <copyright file="AxisRendererBase.cs" company="OxyPlot">
123.6 +// The MIT License (MIT)
123.7 +//
123.8 +// Copyright (c) 2012 Oystein Bjorke
123.9 +//
123.10 +// Permission is hereby granted, free of charge, to any person obtaining a
123.11 +// copy of this software and associated documentation files (the
123.12 +// "Software"), to deal in the Software without restriction, including
123.13 +// without limitation the rights to use, copy, modify, merge, publish,
123.14 +// distribute, sublicense, and/or sell copies of the Software, and to
123.15 +// permit persons to whom the Software is furnished to do so, subject to
123.16 +// the following conditions:
123.17 +//
123.18 +// The above copyright notice and this permission notice shall be included
123.19 +// in all copies or substantial portions of the Software.
123.20 +//
123.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
123.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
123.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
123.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
123.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
123.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
123.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
123.28 +// </copyright>
123.29 +// <summary>
123.30 +// The axis renderer base.
123.31 +// </summary>
123.32 +// --------------------------------------------------------------------------------------------------------------------
123.33 +namespace OxyPlot
123.34 +{
123.35 + using System.Collections.Generic;
123.36 +
123.37 + using OxyPlot.Axes;
123.38 +
123.39 + /// <summary>
123.40 + /// Provides an abstract base class for axis renderers.
123.41 + /// </summary>
123.42 + public abstract class AxisRendererBase
123.43 + {
123.44 + /// <summary>
123.45 + /// The plot.
123.46 + /// </summary>
123.47 + protected readonly PlotModel Plot;
123.48 +
123.49 + /// <summary>
123.50 + /// The render context.
123.51 + /// </summary>
123.52 + protected readonly IRenderContext rc;
123.53 +
123.54 + /// <summary>
123.55 + /// The axis lines pen.
123.56 + /// </summary>
123.57 + protected OxyPen AxislinePen;
123.58 +
123.59 + /// <summary>
123.60 + /// The extra grid lines pen.
123.61 + /// </summary>
123.62 + protected OxyPen ExtraPen;
123.63 +
123.64 + /// <summary>
123.65 + /// The major label values.
123.66 + /// </summary>
123.67 + protected IList<double> MajorLabelValues;
123.68 +
123.69 + /// <summary>
123.70 + /// The major grid lines pen.
123.71 + /// </summary>
123.72 + protected OxyPen MajorPen;
123.73 +
123.74 + /// <summary>
123.75 + /// The major tick pen.
123.76 + /// </summary>
123.77 + protected OxyPen MajorTickPen;
123.78 +
123.79 + /// <summary>
123.80 + /// The major tick values.
123.81 + /// </summary>
123.82 + protected IList<double> MajorTickValues;
123.83 +
123.84 + /// <summary>
123.85 + /// The minor grid lines pen.
123.86 + /// </summary>
123.87 + protected OxyPen MinorPen;
123.88 +
123.89 + /// <summary>
123.90 + /// The minor tick pen.
123.91 + /// </summary>
123.92 + protected OxyPen MinorTickPen;
123.93 +
123.94 + /// <summary>
123.95 + /// The minor tick values.
123.96 + /// </summary>
123.97 + protected IList<double> MinorTickValues;
123.98 +
123.99 + /// <summary>
123.100 + /// The zero grid line pen.
123.101 + /// </summary>
123.102 + protected OxyPen ZeroPen;
123.103 +
123.104 + /// <summary>
123.105 + /// Initializes a new instance of the <see cref="AxisRendererBase"/> class.
123.106 + /// </summary>
123.107 + /// <param name="rc">
123.108 + /// The render context.
123.109 + /// </param>
123.110 + /// <param name="plot">
123.111 + /// The plot.
123.112 + /// </param>
123.113 + protected AxisRendererBase(IRenderContext rc, PlotModel plot)
123.114 + {
123.115 + this.Plot = plot;
123.116 + this.rc = rc;
123.117 + }
123.118 +
123.119 + /// <summary>
123.120 + /// Renders the specified axis.
123.121 + /// </summary>
123.122 + /// <param name="axis">The axis.</param>
123.123 + /// <param name="pass">The pass.</param>
123.124 + public virtual void Render(Axis axis, int pass)
123.125 + {
123.126 + if (axis == null)
123.127 + {
123.128 + return;
123.129 + }
123.130 +
123.131 + axis.GetTickValues(out this.MajorLabelValues, out this.MajorTickValues, out this.MinorTickValues);
123.132 + this.CreatePens(axis);
123.133 + }
123.134 +
123.135 + /// <summary>
123.136 + /// The create pens.
123.137 + /// </summary>
123.138 + /// <param name="axis">
123.139 + /// The axis.
123.140 + /// </param>
123.141 + protected void CreatePens(Axis axis)
123.142 + {
123.143 + this.MinorPen = OxyPen.Create(axis.MinorGridlineColor, axis.MinorGridlineThickness, axis.MinorGridlineStyle);
123.144 + this.MajorPen = OxyPen.Create(axis.MajorGridlineColor, axis.MajorGridlineThickness, axis.MajorGridlineStyle);
123.145 + this.MinorTickPen = OxyPen.Create(axis.TicklineColor, axis.MinorGridlineThickness);
123.146 + this.MajorTickPen = OxyPen.Create(axis.TicklineColor, axis.MajorGridlineThickness);
123.147 + this.ZeroPen = OxyPen.Create(axis.TicklineColor, axis.MajorGridlineThickness);
123.148 + this.ExtraPen = OxyPen.Create(axis.ExtraGridlineColor, axis.ExtraGridlineThickness, axis.ExtraGridlineStyle);
123.149 + this.AxislinePen = OxyPen.Create(axis.AxislineColor, axis.AxislineThickness, axis.AxislineStyle);
123.150 + }
123.151 +
123.152 + /// <summary>
123.153 + /// The get tick positions.
123.154 + /// </summary>
123.155 + /// <param name="axis">
123.156 + /// The axis.
123.157 + /// </param>
123.158 + /// <param name="glt">
123.159 + /// The glt.
123.160 + /// </param>
123.161 + /// <param name="ticksize">
123.162 + /// The ticksize.
123.163 + /// </param>
123.164 + /// <param name="position">
123.165 + /// The position.
123.166 + /// </param>
123.167 + /// <param name="x0">
123.168 + /// The x 0.
123.169 + /// </param>
123.170 + /// <param name="x1">
123.171 + /// The x 1.
123.172 + /// </param>
123.173 + protected void GetTickPositions(
123.174 + Axis axis, TickStyle glt, double ticksize, AxisPosition position, out double x0, out double x1)
123.175 + {
123.176 + x0 = 0;
123.177 + x1 = 0;
123.178 + bool isTopOrLeft = position == AxisPosition.Top || position == AxisPosition.Left;
123.179 + double sign = isTopOrLeft ? -1 : 1;
123.180 + switch (glt)
123.181 + {
123.182 + case TickStyle.Crossing:
123.183 + x0 = -ticksize * sign * 0.75;
123.184 + x1 = ticksize * sign * 0.75;
123.185 + break;
123.186 + case TickStyle.Inside:
123.187 + x0 = -ticksize * sign;
123.188 + break;
123.189 + case TickStyle.Outside:
123.190 + x1 = ticksize * sign;
123.191 + break;
123.192 + }
123.193 + }
123.194 +
123.195 + /// <summary>
123.196 + /// Determines whether the specified value is within the specified range.
123.197 + /// </summary>
123.198 + /// <param name="d">The value to check.</param>
123.199 + /// <param name="min">The minium value of the range.</param>
123.200 + /// <param name="max">The maximum value of the range.</param>
123.201 + /// <returns>
123.202 + /// <c>true</c> if the specified value is within the range; otherwise, <c>false</c>.
123.203 + /// </returns>
123.204 + protected bool IsWithin(double d, double min, double max)
123.205 + {
123.206 + if (d < min)
123.207 + {
123.208 + return false;
123.209 + }
123.210 +
123.211 + if (d > max)
123.212 + {
123.213 + return false;
123.214 + }
123.215 +
123.216 + return true;
123.217 + }
123.218 +
123.219 + }
123.220 +}
123.221 \ No newline at end of file
124.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
124.2 +++ b/External/OxyPlot/OxyPlot/Render/HorizontalAndVerticalAxisRenderer.cs Sat Jun 08 16:53:22 2013 +0000
124.3 @@ -0,0 +1,642 @@
124.4 +// --------------------------------------------------------------------------------------------------------------------
124.5 +// <copyright file="HorizontalAndVerticalAxisRenderer.cs" company="OxyPlot">
124.6 +// The MIT License (MIT)
124.7 +//
124.8 +// Copyright (c) 2012 Oystein Bjorke
124.9 +//
124.10 +// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and
124.11 +// associated documentation files (the "Software"), to deal in the Software without restriction,
124.12 +// including without limitation the rights to use, copy, modify, merge, publish, distribute,
124.13 +// sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is
124.14 +// furnished to do so, subject to the following conditions:
124.15 +//
124.16 +// The above copyright notice and this permission notice shall be included in all copies or substantial
124.17 +// portions of the Software.
124.18 +//
124.19 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT
124.20 +// NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
124.21 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
124.22 +// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
124.23 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
124.24 +// </copyright>
124.25 +// <summary>
124.26 +// Rendering helper class for horizontal and vertical axes (both linear and logarithmic)
124.27 +// </summary>
124.28 +// --------------------------------------------------------------------------------------------------------------------
124.29 +namespace OxyPlot
124.30 +{
124.31 + using System;
124.32 + using System.Collections.Generic;
124.33 + using System.Diagnostics;
124.34 +
124.35 + using OxyPlot.Axes;
124.36 +
124.37 + /// <summary>
124.38 + /// Preovides functionality to render horizontal and vertical axes.
124.39 + /// </summary>
124.40 + public class HorizontalAndVerticalAxisRenderer : AxisRendererBase
124.41 + {
124.42 + /// <summary>
124.43 + /// Initializes a new instance of the <see cref="HorizontalAndVerticalAxisRenderer"/> class.
124.44 + /// </summary>
124.45 + /// <param name="rc">
124.46 + /// The render context.
124.47 + /// </param>
124.48 + /// <param name="plot">
124.49 + /// The plot.
124.50 + /// </param>
124.51 + public HorizontalAndVerticalAxisRenderer(IRenderContext rc, PlotModel plot)
124.52 + : base(rc, plot)
124.53 + {
124.54 + }
124.55 +
124.56 + /// <summary>
124.57 + /// Renders the specified axis.
124.58 + /// </summary>
124.59 + /// <param name="axis">The axis.</param>
124.60 + /// <param name="pass">The pass.</param>
124.61 + public override void Render(Axis axis, int pass)
124.62 + {
124.63 + base.Render(axis, pass);
124.64 +
124.65 + double totalShift = axis.PositionTierMinShift;
124.66 + double tierSize = axis.PositionTierSize - this.Plot.AxisTierDistance;
124.67 +
124.68 + // store properties locally for performance
124.69 + double plotAreaLeft = this.Plot.PlotArea.Left;
124.70 + double plotAreaRight = this.Plot.PlotArea.Right;
124.71 + double plotAreaTop = this.Plot.PlotArea.Top;
124.72 + double plotAreaBottom = this.Plot.PlotArea.Bottom;
124.73 +
124.74 + // Axis position (x or y screen coordinate)
124.75 + double axisPosition = 0;
124.76 + double titlePosition = 0;
124.77 +
124.78 + switch (axis.Position)
124.79 + {
124.80 + case AxisPosition.Left:
124.81 + axisPosition = plotAreaLeft - totalShift;
124.82 + titlePosition = axisPosition - tierSize;
124.83 + break;
124.84 + case AxisPosition.Right:
124.85 + axisPosition = plotAreaRight + totalShift;
124.86 + titlePosition = axisPosition + tierSize;
124.87 + break;
124.88 + case AxisPosition.Top:
124.89 + axisPosition = plotAreaTop - totalShift;
124.90 + titlePosition = axisPosition - tierSize;
124.91 + break;
124.92 + case AxisPosition.Bottom:
124.93 + axisPosition = plotAreaBottom + totalShift;
124.94 + titlePosition = axisPosition + tierSize;
124.95 + break;
124.96 + }
124.97 +
124.98 + if (axis.PositionAtZeroCrossing)
124.99 + {
124.100 + var perpendicularAxis = axis.IsHorizontal() ? this.Plot.DefaultYAxis : this.Plot.DefaultXAxis;
124.101 + axisPosition = perpendicularAxis.Transform(0);
124.102 + }
124.103 +
124.104 + if (pass == 0)
124.105 + {
124.106 + this.RenderMinorItems(axis, axisPosition);
124.107 + }
124.108 +
124.109 + if (pass == 1)
124.110 + {
124.111 + this.RenderMajorItems(axis, axisPosition, titlePosition);
124.112 + }
124.113 + }
124.114 +
124.115 + /// <summary>
124.116 + /// Gets the axis title position, rotation and alignment.
124.117 + /// </summary>
124.118 + /// <param name="axis">
124.119 + /// The axis.
124.120 + /// </param>
124.121 + /// <param name="titlePosition">
124.122 + /// The title position.
124.123 + /// </param>
124.124 + /// <param name="angle">
124.125 + /// The angle.
124.126 + /// </param>
124.127 + /// <param name="halign">
124.128 + /// The horizontal alignment.
124.129 + /// </param>
124.130 + /// <param name="valign">
124.131 + /// The vertical alignment.
124.132 + /// </param>
124.133 + /// <returns>
124.134 + /// The <see cref="ScreenPoint"/>.
124.135 + /// </returns>
124.136 + protected virtual ScreenPoint GetAxisTitlePositionAndAlignment(
124.137 + Axis axis,
124.138 + double titlePosition,
124.139 + ref double angle,
124.140 + ref HorizontalAlignment halign,
124.141 + ref VerticalAlignment valign)
124.142 + {
124.143 + double middle = axis.IsHorizontal()
124.144 + ? Lerp(axis.ScreenMin.X, axis.ScreenMax.X, axis.TitlePosition)
124.145 + : Lerp(axis.ScreenMax.Y, axis.ScreenMin.Y, axis.TitlePosition);
124.146 +
124.147 + if (axis.PositionAtZeroCrossing)
124.148 + {
124.149 + var perpendicularAxis = axis.IsHorizontal() ? this.Plot.DefaultYAxis : this.Plot.DefaultXAxis;
124.150 + middle = perpendicularAxis.Transform(perpendicularAxis.ActualMaximum);
124.151 + }
124.152 +
124.153 + switch (axis.Position)
124.154 + {
124.155 + case AxisPosition.Left:
124.156 + return new ScreenPoint(titlePosition, middle);
124.157 + case AxisPosition.Right:
124.158 + valign = VerticalAlignment.Bottom;
124.159 + return new ScreenPoint(titlePosition, middle);
124.160 + case AxisPosition.Top:
124.161 + halign = HorizontalAlignment.Center;
124.162 + valign = VerticalAlignment.Top;
124.163 + angle = 0;
124.164 + return new ScreenPoint(middle, titlePosition);
124.165 + case AxisPosition.Bottom:
124.166 + halign = HorizontalAlignment.Center;
124.167 + valign = VerticalAlignment.Bottom;
124.168 + angle = 0;
124.169 + return new ScreenPoint(middle, titlePosition);
124.170 + default:
124.171 + throw new ArgumentOutOfRangeException("axis");
124.172 + }
124.173 + }
124.174 +
124.175 + /// <summary>
124.176 + /// Gets the alignments given the specified rotation angle.
124.177 + /// </summary>
124.178 + /// <param name="angle">
124.179 + /// The angle.
124.180 + /// </param>
124.181 + /// <param name="defaultHorizontalAlignment">
124.182 + /// The default horizontal alignment.
124.183 + /// </param>
124.184 + /// <param name="defaultVerticalAlignment">
124.185 + /// The default vertical alignment.
124.186 + /// </param>
124.187 + /// <param name="ha">
124.188 + /// The rotated horizontal alignment.
124.189 + /// </param>
124.190 + /// <param name="va">
124.191 + /// The rotated vertical alignment.
124.192 + /// </param>
124.193 + protected virtual void GetRotatedAlignments(
124.194 + double angle,
124.195 + HorizontalAlignment defaultHorizontalAlignment,
124.196 + VerticalAlignment defaultVerticalAlignment,
124.197 + out HorizontalAlignment ha,
124.198 + out VerticalAlignment va)
124.199 + {
124.200 + ha = defaultHorizontalAlignment;
124.201 + va = defaultVerticalAlignment;
124.202 +
124.203 + Debug.Assert(angle <= 180 && angle >= -180, "Axis angle should be in the interval [-180,180] degrees.");
124.204 +
124.205 + if (angle > -45 && angle < 45)
124.206 + {
124.207 + return;
124.208 + }
124.209 +
124.210 + if (angle > 135 || angle < -135)
124.211 + {
124.212 + ha = (HorizontalAlignment)(-(int)defaultHorizontalAlignment);
124.213 + va = (VerticalAlignment)(-(int)defaultVerticalAlignment);
124.214 + return;
124.215 + }
124.216 +
124.217 + if (angle > 45)
124.218 + {
124.219 + ha = (HorizontalAlignment)((int)defaultVerticalAlignment);
124.220 + va = (VerticalAlignment)(-(int)defaultHorizontalAlignment);
124.221 + return;
124.222 + }
124.223 +
124.224 + if (angle < -45)
124.225 + {
124.226 + ha = (HorizontalAlignment)(-(int)defaultVerticalAlignment);
124.227 + va = (VerticalAlignment)((int)defaultHorizontalAlignment);
124.228 + }
124.229 + }
124.230 +
124.231 + /// <summary>
124.232 + /// Linear interpolation
124.233 + /// http://en.wikipedia.org/wiki/Linear_interpolation
124.234 + /// </summary>
124.235 + /// <param name="x0">
124.236 + /// The x0.
124.237 + /// </param>
124.238 + /// <param name="x1">
124.239 + /// The x1.
124.240 + /// </param>
124.241 + /// <param name="f">
124.242 + /// The interpolation factor.
124.243 + /// </param>
124.244 + /// <returns>
124.245 + /// The interpolated value.
124.246 + /// </returns>
124.247 + private static double Lerp(double x0, double x1, double f)
124.248 + {
124.249 + return (x0 * (1 - f)) + (x1 * f);
124.250 + }
124.251 +
124.252 + /// <summary>
124.253 + /// Snaps v to value if it is within the the specified distance.
124.254 + /// </summary>
124.255 + /// <param name="target">
124.256 + /// The target value.
124.257 + /// </param>
124.258 + /// <param name="v">
124.259 + /// The value to snap.
124.260 + /// </param>
124.261 + /// <param name="eps">
124.262 + /// The distance tolerance.
124.263 + /// </param>
124.264 + private static void SnapTo(double target, ref double v, double eps = 0.5)
124.265 + {
124.266 + if (v > target - eps && v < target + eps)
124.267 + {
124.268 + v = target;
124.269 + }
124.270 + }
124.271 +
124.272 + /// <summary>
124.273 + /// Renders the axis title.
124.274 + /// </summary>
124.275 + /// <param name="axis">
124.276 + /// The axis.
124.277 + /// </param>
124.278 + /// <param name="titlePosition">
124.279 + /// The title position.
124.280 + /// </param>
124.281 + private void RenderAxisTitle(Axis axis, double titlePosition)
124.282 + {
124.283 + bool isHorizontal = axis.IsHorizontal();
124.284 +
124.285 + OxySize? maxSize = null;
124.286 +
124.287 + if (axis.ClipTitle)
124.288 + {
124.289 + // Calculate the title clipping dimensions
124.290 + double screenLength = isHorizontal
124.291 + ? Math.Abs(axis.ScreenMax.X - axis.ScreenMin.X)
124.292 + : Math.Abs(axis.ScreenMax.Y - axis.ScreenMin.Y);
124.293 +
124.294 + maxSize = new OxySize(screenLength * axis.TitleClippingLength, double.MaxValue);
124.295 + }
124.296 +
124.297 + double angle = -90;
124.298 +
124.299 + var halign = HorizontalAlignment.Center;
124.300 + var valign = VerticalAlignment.Top;
124.301 +
124.302 + var lpt = this.GetAxisTitlePositionAndAlignment(axis, titlePosition, ref angle, ref halign, ref valign);
124.303 +
124.304 + this.rc.SetToolTip(axis.ToolTip);
124.305 + this.rc.DrawMathText(
124.306 + lpt,
124.307 + axis.ActualTitle,
124.308 + axis.ActualTitleColor,
124.309 + axis.ActualTitleFont,
124.310 + axis.ActualTitleFontSize,
124.311 + axis.ActualTitleFontWeight,
124.312 + angle,
124.313 + halign,
124.314 + valign,
124.315 + maxSize);
124.316 + this.rc.SetToolTip(null);
124.317 + }
124.318 +
124.319 + /// <summary>
124.320 + /// Renders the major items.
124.321 + /// </summary>
124.322 + /// <param name="axis">
124.323 + /// The axis.
124.324 + /// </param>
124.325 + /// <param name="axisPosition">
124.326 + /// The axis position.
124.327 + /// </param>
124.328 + /// <param name="titlePosition">
124.329 + /// The title position.
124.330 + /// </param>
124.331 + private void RenderMajorItems(Axis axis, double axisPosition, double titlePosition)
124.332 + {
124.333 + double eps = axis.ActualMinorStep * 1e-3;
124.334 +
124.335 + double actualMinimum = axis.ActualMinimum;
124.336 + double actualMaximum = axis.ActualMaximum;
124.337 +
124.338 + double plotAreaLeft = this.Plot.PlotArea.Left;
124.339 + double plotAreaRight = this.Plot.PlotArea.Right;
124.340 + double plotAreaTop = this.Plot.PlotArea.Top;
124.341 + double plotAreaBottom = this.Plot.PlotArea.Bottom;
124.342 + bool isHorizontal = axis.IsHorizontal();
124.343 +
124.344 + double a0;
124.345 + double a1;
124.346 + var majorSegments = new List<ScreenPoint>();
124.347 + var majorTickSegments = new List<ScreenPoint>();
124.348 + this.GetTickPositions(axis, axis.TickStyle, axis.MajorTickSize, axis.Position, out a0, out a1);
124.349 +
124.350 + foreach (double value in this.MajorTickValues)
124.351 + {
124.352 + if (value < actualMinimum - eps || value > actualMaximum + eps)
124.353 + {
124.354 + continue;
124.355 + }
124.356 +
124.357 + if (axis.PositionAtZeroCrossing && Math.Abs(value) < eps)
124.358 + {
124.359 + continue;
124.360 + }
124.361 +
124.362 + double transformedValue = axis.Transform(value);
124.363 + if (isHorizontal)
124.364 + {
124.365 + SnapTo(plotAreaLeft, ref transformedValue);
124.366 + SnapTo(plotAreaRight, ref transformedValue);
124.367 + }
124.368 + else
124.369 + {
124.370 + SnapTo(plotAreaTop, ref transformedValue);
124.371 + SnapTo(plotAreaBottom, ref transformedValue);
124.372 + }
124.373 +
124.374 + if (this.MajorPen != null)
124.375 + {
124.376 + if (isHorizontal)
124.377 + {
124.378 + majorSegments.Add(new ScreenPoint(transformedValue, plotAreaTop));
124.379 + majorSegments.Add(new ScreenPoint(transformedValue, plotAreaBottom));
124.380 + }
124.381 + else
124.382 + {
124.383 + majorSegments.Add(new ScreenPoint(plotAreaLeft, transformedValue));
124.384 + majorSegments.Add(new ScreenPoint(plotAreaRight, transformedValue));
124.385 + }
124.386 + }
124.387 +
124.388 + if (axis.TickStyle != TickStyle.None)
124.389 + {
124.390 + if (isHorizontal)
124.391 + {
124.392 + majorTickSegments.Add(new ScreenPoint(transformedValue, axisPosition + a0));
124.393 + majorTickSegments.Add(new ScreenPoint(transformedValue, axisPosition + a1));
124.394 + }
124.395 + else
124.396 + {
124.397 + majorTickSegments.Add(new ScreenPoint(axisPosition + a0, transformedValue));
124.398 + majorTickSegments.Add(new ScreenPoint(axisPosition + a1, transformedValue));
124.399 + }
124.400 + }
124.401 + }
124.402 +
124.403 + // Render the axis labels (numbers or category names)
124.404 + foreach (double value in this.MajorLabelValues)
124.405 + {
124.406 + if (value < actualMinimum - eps || value > actualMaximum + eps)
124.407 + {
124.408 + continue;
124.409 + }
124.410 +
124.411 + if (axis.PositionAtZeroCrossing && Math.Abs(value) < eps)
124.412 + {
124.413 + continue;
124.414 + }
124.415 +
124.416 + double transformedValue = axis.Transform(value);
124.417 + if (isHorizontal)
124.418 + {
124.419 + SnapTo(plotAreaLeft, ref transformedValue);
124.420 + SnapTo(plotAreaRight, ref transformedValue);
124.421 + }
124.422 + else
124.423 + {
124.424 + SnapTo(plotAreaTop, ref transformedValue);
124.425 + SnapTo(plotAreaBottom, ref transformedValue);
124.426 + }
124.427 +
124.428 + var pt = new ScreenPoint();
124.429 + var ha = HorizontalAlignment.Right;
124.430 + var va = VerticalAlignment.Middle;
124.431 + switch (axis.Position)
124.432 + {
124.433 + case AxisPosition.Left:
124.434 + pt = new ScreenPoint(axisPosition + a1 - axis.AxisTickToLabelDistance, transformedValue);
124.435 + this.GetRotatedAlignments(
124.436 + axis.Angle, HorizontalAlignment.Right, VerticalAlignment.Middle, out ha, out va);
124.437 + break;
124.438 + case AxisPosition.Right:
124.439 + pt = new ScreenPoint(axisPosition + a1 + axis.AxisTickToLabelDistance, transformedValue);
124.440 + this.GetRotatedAlignments(
124.441 + axis.Angle, HorizontalAlignment.Left, VerticalAlignment.Middle, out ha, out va);
124.442 + break;
124.443 + case AxisPosition.Top:
124.444 + pt = new ScreenPoint(transformedValue, axisPosition + a1 - axis.AxisTickToLabelDistance);
124.445 + this.GetRotatedAlignments(
124.446 + axis.Angle, HorizontalAlignment.Center, VerticalAlignment.Bottom, out ha, out va);
124.447 + break;
124.448 + case AxisPosition.Bottom:
124.449 + pt = new ScreenPoint(transformedValue, axisPosition + a1 + axis.AxisTickToLabelDistance);
124.450 + this.GetRotatedAlignments(
124.451 + axis.Angle, HorizontalAlignment.Center, VerticalAlignment.Top, out ha, out va);
124.452 + break;
124.453 + }
124.454 +
124.455 + string text = axis.FormatValue(value);
124.456 + this.rc.DrawMathText(
124.457 + pt,
124.458 + text,
124.459 + axis.ActualTextColor,
124.460 + axis.ActualFont,
124.461 + axis.ActualFontSize,
124.462 + axis.ActualFontWeight,
124.463 + axis.Angle,
124.464 + ha,
124.465 + va);
124.466 + }
124.467 +
124.468 + // Draw the zero crossing line
124.469 + if (axis.PositionAtZeroCrossing && this.ZeroPen != null)
124.470 + {
124.471 + double t0 = axis.Transform(0);
124.472 + if (isHorizontal)
124.473 + {
124.474 + this.rc.DrawLine(t0, plotAreaTop, t0, plotAreaBottom, this.ZeroPen);
124.475 + }
124.476 + else
124.477 + {
124.478 + this.rc.DrawLine(plotAreaLeft, t0, plotAreaRight, t0, this.ZeroPen);
124.479 + }
124.480 + }
124.481 +
124.482 + // Draw extra grid lines
124.483 + if (axis.ExtraGridlines != null && this.ExtraPen != null)
124.484 + {
124.485 + foreach (double value in axis.ExtraGridlines)
124.486 + {
124.487 + if (!this.IsWithin(value, actualMinimum, actualMaximum))
124.488 + {
124.489 + continue;
124.490 + }
124.491 +
124.492 + double transformedValue = axis.Transform(value);
124.493 + if (isHorizontal)
124.494 + {
124.495 + this.rc.DrawLine(transformedValue, plotAreaTop, transformedValue, plotAreaBottom, this.ExtraPen);
124.496 + }
124.497 + else
124.498 + {
124.499 + this.rc.DrawLine(plotAreaLeft, transformedValue, plotAreaRight, transformedValue, this.ExtraPen);
124.500 + }
124.501 + }
124.502 + }
124.503 +
124.504 + // Draw the axis line (across the tick marks)
124.505 + if (isHorizontal)
124.506 + {
124.507 + this.rc.DrawLine(
124.508 + axis.Transform(actualMinimum),
124.509 + axisPosition,
124.510 + axis.Transform(actualMaximum),
124.511 + axisPosition,
124.512 + this.AxislinePen);
124.513 + }
124.514 + else
124.515 + {
124.516 + this.rc.DrawLine(
124.517 + axisPosition,
124.518 + axis.Transform(actualMinimum),
124.519 + axisPosition,
124.520 + axis.Transform(actualMaximum),
124.521 + this.AxislinePen);
124.522 + }
124.523 +
124.524 + // Draw the axis title
124.525 + if (!string.IsNullOrEmpty(axis.ActualTitle))
124.526 + {
124.527 + this.RenderAxisTitle(axis, titlePosition);
124.528 + }
124.529 +
124.530 + if (this.MajorPen != null)
124.531 + {
124.532 + this.rc.DrawLineSegments(majorSegments, this.MajorPen);
124.533 + }
124.534 +
124.535 + if (this.MajorTickPen != null)
124.536 + {
124.537 + this.rc.DrawLineSegments(majorTickSegments, this.MajorTickPen);
124.538 + }
124.539 + }
124.540 +
124.541 + /// <summary>
124.542 + /// Renders the minor items.
124.543 + /// </summary>
124.544 + /// <param name="axis">
124.545 + /// The axis.
124.546 + /// </param>
124.547 + /// <param name="axisPosition">
124.548 + /// The axis position.
124.549 + /// </param>
124.550 + private void RenderMinorItems(Axis axis, double axisPosition)
124.551 + {
124.552 + double eps = axis.ActualMinorStep * 1e-3;
124.553 + double actualMinimum = axis.ActualMinimum;
124.554 + double actualMaximum = axis.ActualMaximum;
124.555 +
124.556 + double plotAreaLeft = this.Plot.PlotArea.Left;
124.557 + double plotAreaRight = this.Plot.PlotArea.Right;
124.558 + double plotAreaTop = this.Plot.PlotArea.Top;
124.559 + double plotAreaBottom = this.Plot.PlotArea.Bottom;
124.560 + bool isHorizontal = axis.IsHorizontal();
124.561 +
124.562 + double a0;
124.563 + double a1;
124.564 + var minorSegments = new List<ScreenPoint>();
124.565 + var minorTickSegments = new List<ScreenPoint>();
124.566 + this.GetTickPositions(axis, axis.TickStyle, axis.MinorTickSize, axis.Position, out a0, out a1);
124.567 +
124.568 + foreach (double value in this.MinorTickValues)
124.569 + {
124.570 + if (value < actualMinimum - eps || value > actualMaximum + eps)
124.571 + {
124.572 + continue;
124.573 + }
124.574 +
124.575 + if (this.MajorTickValues.Contains(value))
124.576 + {
124.577 + continue;
124.578 + }
124.579 +
124.580 + if (axis.PositionAtZeroCrossing && Math.Abs(value) < eps)
124.581 + {
124.582 + continue;
124.583 + }
124.584 +
124.585 + double transformedValue = axis.Transform(value);
124.586 +
124.587 + if (isHorizontal)
124.588 + {
124.589 + SnapTo(plotAreaLeft, ref transformedValue);
124.590 + SnapTo(plotAreaRight, ref transformedValue);
124.591 + }
124.592 + else
124.593 + {
124.594 + SnapTo(plotAreaTop, ref transformedValue);
124.595 + SnapTo(plotAreaBottom, ref transformedValue);
124.596 + }
124.597 +
124.598 + // Draw the minor grid line
124.599 + if (this.MinorPen != null)
124.600 + {
124.601 + if (isHorizontal)
124.602 + {
124.603 + minorSegments.Add(new ScreenPoint(transformedValue, plotAreaTop));
124.604 + minorSegments.Add(new ScreenPoint(transformedValue, plotAreaBottom));
124.605 + }
124.606 + else
124.607 + {
124.608 + if (transformedValue < plotAreaTop || transformedValue > plotAreaBottom)
124.609 + {
124.610 + }
124.611 +
124.612 + minorSegments.Add(new ScreenPoint(plotAreaLeft, transformedValue));
124.613 + minorSegments.Add(new ScreenPoint(plotAreaRight, transformedValue));
124.614 + }
124.615 + }
124.616 +
124.617 + // Draw the minor tick
124.618 + if (axis.TickStyle != TickStyle.None)
124.619 + {
124.620 + if (isHorizontal)
124.621 + {
124.622 + minorTickSegments.Add(new ScreenPoint(transformedValue, axisPosition + a0));
124.623 + minorTickSegments.Add(new ScreenPoint(transformedValue, axisPosition + a1));
124.624 + }
124.625 + else
124.626 + {
124.627 + minorTickSegments.Add(new ScreenPoint(axisPosition + a0, transformedValue));
124.628 + minorTickSegments.Add(new ScreenPoint(axisPosition + a1, transformedValue));
124.629 + }
124.630 + }
124.631 + }
124.632 +
124.633 + // Draw all the line segments);
124.634 + if (this.MinorPen != null)
124.635 + {
124.636 + this.rc.DrawLineSegments(minorSegments, this.MinorPen);
124.637 + }
124.638 +
124.639 + if (this.MinorTickPen != null)
124.640 + {
124.641 + this.rc.DrawLineSegments(minorTickSegments, this.MinorTickPen);
124.642 + }
124.643 + }
124.644 + }
124.645 +}
124.646 \ No newline at end of file
125.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
125.2 +++ b/External/OxyPlot/OxyPlot/Render/IRenderContext.cs Sat Jun 08 16:53:22 2013 +0000
125.3 @@ -0,0 +1,400 @@
125.4 +// --------------------------------------------------------------------------------------------------------------------
125.5 +// <copyright file="IRenderContext.cs" company="OxyPlot">
125.6 +// The MIT License (MIT)
125.7 +//
125.8 +// Copyright (c) 2012 Oystein Bjorke
125.9 +//
125.10 +// Permission is hereby granted, free of charge, to any person obtaining a
125.11 +// copy of this software and associated documentation files (the
125.12 +// "Software"), to deal in the Software without restriction, including
125.13 +// without limitation the rights to use, copy, modify, merge, publish,
125.14 +// distribute, sublicense, and/or sell copies of the Software, and to
125.15 +// permit persons to whom the Software is furnished to do so, subject to
125.16 +// the following conditions:
125.17 +//
125.18 +// The above copyright notice and this permission notice shall be included
125.19 +// in all copies or substantial portions of the Software.
125.20 +//
125.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
125.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
125.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
125.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
125.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
125.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
125.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
125.28 +// </copyright>
125.29 +// <summary>
125.30 +// Render context interface.
125.31 +// </summary>
125.32 +// --------------------------------------------------------------------------------------------------------------------
125.33 +namespace OxyPlot
125.34 +{
125.35 + using System.Collections.Generic;
125.36 +
125.37 + /// <summary>
125.38 + /// Defines rendering functionality.
125.39 + /// </summary>
125.40 + public interface IRenderContext
125.41 + {
125.42 + /// <summary>
125.43 + /// Gets a value indicating whether the context renders to screen.
125.44 + /// </summary>
125.45 + /// <value>
125.46 + /// <c>true</c> if the context renders to screen; otherwise, <c>false</c>.
125.47 + /// </value>
125.48 + bool RendersToScreen { get; }
125.49 +
125.50 + /// <summary>
125.51 + /// Draws an ellipse.
125.52 + /// </summary>
125.53 + /// <param name="rect">
125.54 + /// The rectangle.
125.55 + /// </param>
125.56 + /// <param name="fill">
125.57 + /// The fill color.
125.58 + /// </param>
125.59 + /// <param name="stroke">
125.60 + /// The stroke color.
125.61 + /// </param>
125.62 + /// <param name="thickness">
125.63 + /// The thickness.
125.64 + /// </param>
125.65 + void DrawEllipse(OxyRect rect, OxyColor fill, OxyColor stroke, double thickness = 1.0);
125.66 +
125.67 + /// <summary>
125.68 + /// Draws the collection of ellipses, where all have the same stroke and fill.
125.69 + /// This performs better than calling DrawEllipse multiple times.
125.70 + /// </summary>
125.71 + /// <param name="rectangles">
125.72 + /// The rectangles.
125.73 + /// </param>
125.74 + /// <param name="fill">
125.75 + /// The fill color.
125.76 + /// </param>
125.77 + /// <param name="stroke">
125.78 + /// The stroke color.
125.79 + /// </param>
125.80 + /// <param name="thickness">
125.81 + /// The stroke thickness.
125.82 + /// </param>
125.83 + void DrawEllipses(IList<OxyRect> rectangles, OxyColor fill, OxyColor stroke, double thickness = 1.0);
125.84 +
125.85 + /// <summary>
125.86 + /// Draws the polyline from the specified points.
125.87 + /// </summary>
125.88 + /// <param name="points">
125.89 + /// The points.
125.90 + /// </param>
125.91 + /// <param name="stroke">
125.92 + /// The stroke color.
125.93 + /// </param>
125.94 + /// <param name="thickness">
125.95 + /// The stroke thickness.
125.96 + /// </param>
125.97 + /// <param name="dashArray">
125.98 + /// The dash array.
125.99 + /// </param>
125.100 + /// <param name="lineJoin">
125.101 + /// The line join type.
125.102 + /// </param>
125.103 + /// <param name="aliased">
125.104 + /// if set to <c>true</c> the shape will be aliased.
125.105 + /// </param>
125.106 + void DrawLine(
125.107 + IList<ScreenPoint> points,
125.108 + OxyColor stroke,
125.109 + double thickness = 1.0,
125.110 + double[] dashArray = null,
125.111 + OxyPenLineJoin lineJoin = OxyPenLineJoin.Miter,
125.112 + bool aliased = false);
125.113 +
125.114 + /// <summary>
125.115 + /// Draws the multiple line segments defined by points (0,1) (2,3) (4,5) etc.
125.116 + /// This should have better performance than calling DrawLine for each segment.
125.117 + /// </summary>
125.118 + /// <param name="points">
125.119 + /// The points.
125.120 + /// </param>
125.121 + /// <param name="stroke">
125.122 + /// The stroke color.
125.123 + /// </param>
125.124 + /// <param name="thickness">
125.125 + /// The stroke thickness.
125.126 + /// </param>
125.127 + /// <param name="dashArray">
125.128 + /// The dash array.
125.129 + /// </param>
125.130 + /// <param name="lineJoin">
125.131 + /// The line join type.
125.132 + /// </param>
125.133 + /// <param name="aliased">
125.134 + /// if set to <c>true</c> the shape will be aliased.
125.135 + /// </param>
125.136 + void DrawLineSegments(
125.137 + IList<ScreenPoint> points,
125.138 + OxyColor stroke,
125.139 + double thickness = 1.0,
125.140 + double[] dashArray = null,
125.141 + OxyPenLineJoin lineJoin = OxyPenLineJoin.Miter,
125.142 + bool aliased = false);
125.143 +
125.144 + /// <summary>
125.145 + /// Draws the polygon from the specified points. The polygon can have stroke and/or fill.
125.146 + /// </summary>
125.147 + /// <param name="points">
125.148 + /// The points.
125.149 + /// </param>
125.150 + /// <param name="fill">
125.151 + /// The fill color.
125.152 + /// </param>
125.153 + /// <param name="stroke">
125.154 + /// The stroke color.
125.155 + /// </param>
125.156 + /// <param name="thickness">
125.157 + /// The stroke thickness.
125.158 + /// </param>
125.159 + /// <param name="dashArray">
125.160 + /// The dash array.
125.161 + /// </param>
125.162 + /// <param name="lineJoin">
125.163 + /// The line join type.
125.164 + /// </param>
125.165 + /// <param name="aliased">
125.166 + /// if set to <c>true</c> the shape will be aliased.
125.167 + /// </param>
125.168 + void DrawPolygon(
125.169 + IList<ScreenPoint> points,
125.170 + OxyColor fill,
125.171 + OxyColor stroke,
125.172 + double thickness = 1.0,
125.173 + double[] dashArray = null,
125.174 + OxyPenLineJoin lineJoin = OxyPenLineJoin.Miter,
125.175 + bool aliased = false);
125.176 +
125.177 + /// <summary>
125.178 + /// Draws a collection of polygons, where all polygons have the same stroke and fill.
125.179 + /// This performs better than calling DrawPolygon multiple times.
125.180 + /// </summary>
125.181 + /// <param name="polygons">
125.182 + /// The polygons.
125.183 + /// </param>
125.184 + /// <param name="fill">
125.185 + /// The fill color.
125.186 + /// </param>
125.187 + /// <param name="stroke">
125.188 + /// The stroke color.
125.189 + /// </param>
125.190 + /// <param name="thickness">
125.191 + /// The stroke thickness.
125.192 + /// </param>
125.193 + /// <param name="dashArray">
125.194 + /// The dash array.
125.195 + /// </param>
125.196 + /// <param name="lineJoin">
125.197 + /// The line join type.
125.198 + /// </param>
125.199 + /// <param name="aliased">
125.200 + /// if set to <c>true</c> the shape will be aliased.
125.201 + /// </param>
125.202 + void DrawPolygons(
125.203 + IList<IList<ScreenPoint>> polygons,
125.204 + OxyColor fill,
125.205 + OxyColor stroke,
125.206 + double thickness = 1.0,
125.207 + double[] dashArray = null,
125.208 + OxyPenLineJoin lineJoin = OxyPenLineJoin.Miter,
125.209 + bool aliased = false);
125.210 +
125.211 + /// <summary>
125.212 + /// Draws the rectangle.
125.213 + /// </summary>
125.214 + /// <param name="rect">
125.215 + /// The rectangle.
125.216 + /// </param>
125.217 + /// <param name="fill">
125.218 + /// The fill color.
125.219 + /// </param>
125.220 + /// <param name="stroke">
125.221 + /// The stroke color.
125.222 + /// </param>
125.223 + /// <param name="thickness">
125.224 + /// The stroke thickness.
125.225 + /// </param>
125.226 + void DrawRectangle(OxyRect rect, OxyColor fill, OxyColor stroke, double thickness = 1.0);
125.227 +
125.228 + /// <summary>
125.229 + /// Draws a collection of rectangles, where all have the same stroke and fill.
125.230 + /// This performs better than calling DrawRectangle multiple times.
125.231 + /// </summary>
125.232 + /// <param name="rectangles">
125.233 + /// The rectangles.
125.234 + /// </param>
125.235 + /// <param name="fill">
125.236 + /// The fill color.
125.237 + /// </param>
125.238 + /// <param name="stroke">
125.239 + /// The stroke color.
125.240 + /// </param>
125.241 + /// <param name="thickness">
125.242 + /// The stroke thickness.
125.243 + /// </param>
125.244 + void DrawRectangles(IList<OxyRect> rectangles, OxyColor fill, OxyColor stroke, double thickness = 1.0);
125.245 +
125.246 + /// <summary>
125.247 + /// Draws the text.
125.248 + /// </summary>
125.249 + /// <param name="p">
125.250 + /// The position.
125.251 + /// </param>
125.252 + /// <param name="text">
125.253 + /// The text.
125.254 + /// </param>
125.255 + /// <param name="fill">
125.256 + /// The fill color.
125.257 + /// </param>
125.258 + /// <param name="fontFamily">
125.259 + /// The font family.
125.260 + /// </param>
125.261 + /// <param name="fontSize">
125.262 + /// Size of the font.
125.263 + /// </param>
125.264 + /// <param name="fontWeight">
125.265 + /// The font weight.
125.266 + /// </param>
125.267 + /// <param name="rotate">
125.268 + /// The rotation angle.
125.269 + /// </param>
125.270 + /// <param name="halign">
125.271 + /// The horizontal alignment.
125.272 + /// </param>
125.273 + /// <param name="valign">
125.274 + /// The vertical alignment.
125.275 + /// </param>
125.276 + /// <param name="maxSize">
125.277 + /// The maximum size of the text.
125.278 + /// </param>
125.279 + void DrawText(
125.280 + ScreenPoint p,
125.281 + string text,
125.282 + OxyColor fill,
125.283 + string fontFamily = null,
125.284 + double fontSize = 10,
125.285 + double fontWeight = 500,
125.286 + double rotate = 0,
125.287 + HorizontalAlignment halign = HorizontalAlignment.Left,
125.288 + VerticalAlignment valign = VerticalAlignment.Top,
125.289 + OxySize? maxSize = null);
125.290 +
125.291 + /// <summary>
125.292 + /// Measures the text.
125.293 + /// </summary>
125.294 + /// <param name="text">
125.295 + /// The text.
125.296 + /// </param>
125.297 + /// <param name="fontFamily">
125.298 + /// The font family.
125.299 + /// </param>
125.300 + /// <param name="fontSize">
125.301 + /// Size of the font.
125.302 + /// </param>
125.303 + /// <param name="fontWeight">
125.304 + /// The font weight.
125.305 + /// </param>
125.306 + /// <returns>
125.307 + /// The text size.
125.308 + /// </returns>
125.309 + OxySize MeasureText(string text, string fontFamily = null, double fontSize = 10, double fontWeight = 500);
125.310 +
125.311 + /// <summary>
125.312 + /// Sets the tool tip for the following items.
125.313 + /// </summary>
125.314 + /// <params>
125.315 + /// This is only used in the plot controls.
125.316 + /// </params>
125.317 + /// <param name="text">
125.318 + /// The text in the tooltip.
125.319 + /// </param>
125.320 + void SetToolTip(string text);
125.321 +
125.322 + /// <summary>
125.323 + /// Cleans up resources not in use.
125.324 + /// </summary>
125.325 + /// <remarks>
125.326 + /// This method is called at the end of each rendering.
125.327 + /// </remarks>
125.328 + void CleanUp();
125.329 +
125.330 + /// <summary>
125.331 + /// Gets the size of the specified image.
125.332 + /// </summary>
125.333 + /// <param name="source">The image source.</param>
125.334 + /// <returns>The image info.</returns>
125.335 + OxyImageInfo GetImageInfo(OxyImage source);
125.336 +
125.337 + /// <summary>
125.338 + /// Draws the specified portion of the specified <see cref="OxyImage"/> at the specified location and with the specified size.
125.339 + /// </summary>
125.340 + /// <param name="source">The source.</param>
125.341 + /// <param name="srcX">The x-coordinate of the upper-left corner of the portion of the source image to draw.</param>
125.342 + /// <param name="srcY">The y-coordinate of the upper-left corner of the portion of the source image to draw.</param>
125.343 + /// <param name="srcWidth">Width of the portion of the source image to draw.</param>
125.344 + /// <param name="srcHeight">Height of the portion of the source image to draw.</param>
125.345 + /// <param name="destX">The x-coordinate of the upper-left corner of drawn image.</param>
125.346 + /// <param name="destY">The y-coordinate of the upper-left corner of drawn image.</param>
125.347 + /// <param name="destWidth">The width of the drawn image.</param>
125.348 + /// <param name="destHeight">The height of the drawn image.</param>
125.349 + /// <param name="opacity">The opacity.</param>
125.350 + /// <param name="interpolate">interpolate if set to <c>true</c>.</param>
125.351 + void DrawImage(OxyImage source, uint srcX, uint srcY, uint srcWidth, uint srcHeight, double destX, double destY, double destWidth, double destHeight, double opacity, bool interpolate);
125.352 +
125.353 + /// <summary>
125.354 + /// Sets the clip rectangle.
125.355 + /// </summary>
125.356 + /// <param name="rect">The clip rectangle.</param>
125.357 + /// <returns>True if the clip rectangle was set.</returns>
125.358 + bool SetClip(OxyRect rect);
125.359 +
125.360 + /// <summary>
125.361 + /// Resets the clip rectangle.
125.362 + /// </summary>
125.363 + void ResetClip();
125.364 + }
125.365 +
125.366 + /// <summary>
125.367 + /// Provides information about the size of an image.
125.368 + /// </summary>
125.369 + public class OxyImageInfo
125.370 + {
125.371 + /// <summary>
125.372 + /// Gets or sets the width in pixels.
125.373 + /// </summary>
125.374 + /// <value>
125.375 + /// The width.
125.376 + /// </value>
125.377 + public uint Width { get; set; }
125.378 +
125.379 + /// <summary>
125.380 + /// Gets or sets the height in pixels.
125.381 + /// </summary>
125.382 + /// <value>
125.383 + /// The height.
125.384 + /// </value>
125.385 + public uint Height { get; set; }
125.386 +
125.387 + /// <summary>
125.388 + /// Gets or sets the horizontal resolution in dpi.
125.389 + /// </summary>
125.390 + /// <value>
125.391 + /// The dpi X.
125.392 + /// </value>
125.393 + public double DpiX { get; set; }
125.394 +
125.395 + /// <summary>
125.396 + /// Gets or sets the vertical resolution in dpi.
125.397 + /// </summary>
125.398 + /// <value>
125.399 + /// The dpi Y.
125.400 + /// </value>
125.401 + public double DpiY { get; set; }
125.402 + }
125.403 +}
125.404 \ No newline at end of file
126.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
126.2 +++ b/External/OxyPlot/OxyPlot/Render/MagnitudeAxisRenderer.cs Sat Jun 08 16:53:22 2013 +0000
126.3 @@ -0,0 +1,145 @@
126.4 +// --------------------------------------------------------------------------------------------------------------------
126.5 +// <copyright file="MagnitudeAxisRenderer.cs" company="OxyPlot">
126.6 +// The MIT License (MIT)
126.7 +//
126.8 +// Copyright (c) 2012 Oystein Bjorke
126.9 +//
126.10 +// Permission is hereby granted, free of charge, to any person obtaining a
126.11 +// copy of this software and associated documentation files (the
126.12 +// "Software"), to deal in the Software without restriction, including
126.13 +// without limitation the rights to use, copy, modify, merge, publish,
126.14 +// distribute, sublicense, and/or sell copies of the Software, and to
126.15 +// permit persons to whom the Software is furnished to do so, subject to
126.16 +// the following conditions:
126.17 +//
126.18 +// The above copyright notice and this permission notice shall be included
126.19 +// in all copies or substantial portions of the Software.
126.20 +//
126.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
126.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
126.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
126.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
126.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
126.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
126.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
126.28 +// </copyright>
126.29 +// <summary>
126.30 +// The magnitude axis renderer.
126.31 +// </summary>
126.32 +// --------------------------------------------------------------------------------------------------------------------
126.33 +namespace OxyPlot
126.34 +{
126.35 + using System;
126.36 + using System.Collections.Generic;
126.37 +
126.38 + using OxyPlot.Axes;
126.39 +
126.40 + /// <summary>
126.41 + /// Provides functionality to render <see cref="MagnitudeAxis"/>.
126.42 + /// </summary>
126.43 + public class MagnitudeAxisRenderer : AxisRendererBase
126.44 + {
126.45 + /// <summary>
126.46 + /// Initializes a new instance of the <see cref="MagnitudeAxisRenderer"/> class.
126.47 + /// </summary>
126.48 + /// <param name="rc">
126.49 + /// The render context.
126.50 + /// </param>
126.51 + /// <param name="plot">
126.52 + /// The plot.
126.53 + /// </param>
126.54 + public MagnitudeAxisRenderer(IRenderContext rc, PlotModel plot)
126.55 + : base(rc, plot)
126.56 + {
126.57 + }
126.58 +
126.59 + /// <summary>
126.60 + /// Renders the specified axis.
126.61 + /// </summary>
126.62 + /// <param name="axis">The axis.</param>
126.63 + /// <param name="pass">The pass.</param>
126.64 + /// <exception cref="System.NullReferenceException">Angle axis should not be null.</exception>
126.65 + public override void Render(Axis axis, int pass)
126.66 + {
126.67 + base.Render(axis, pass);
126.68 +
126.69 + var angleAxis = this.Plot.DefaultAngleAxis as Axis;
126.70 + if (axis.RelatedAxis != null)
126.71 + {
126.72 + angleAxis = axis.RelatedAxis;
126.73 + }
126.74 +
126.75 + if (angleAxis == null)
126.76 + {
126.77 + throw new NullReferenceException("Angle axis should not be null.");
126.78 + }
126.79 +
126.80 + if (axis.ShowMinorTicks)
126.81 + {
126.82 + // GetVerticalTickPositions(axis, axis.TickStyle, axis.MinorTickSize, out y0, out y1);
126.83 +
126.84 + foreach (double xValue in this.MinorTickValues)
126.85 + {
126.86 + if (xValue < axis.ActualMinimum || xValue > axis.ActualMaximum)
126.87 + {
126.88 + continue;
126.89 + }
126.90 +
126.91 + if (this.MajorTickValues.Contains(xValue))
126.92 + {
126.93 + continue;
126.94 + }
126.95 +
126.96 + var pts = new List<ScreenPoint>();
126.97 + for (double th = angleAxis.ActualMinimum;
126.98 + th <= angleAxis.ActualMaximum + angleAxis.MinorStep * 0.01;
126.99 + th += angleAxis.MinorStep * 0.1)
126.100 + {
126.101 + pts.Add(axis.Transform(xValue, th, angleAxis));
126.102 + }
126.103 +
126.104 + if (this.MinorPen != null)
126.105 + {
126.106 + this.rc.DrawLine(pts, this.MinorPen.Color, this.MinorPen.Thickness, this.MinorPen.DashArray);
126.107 + }
126.108 +
126.109 + // RenderGridline(x, y + y0, x, y + y1, minorTickPen);
126.110 + }
126.111 + }
126.112 +
126.113 + // GetVerticalTickPositions(axis, axis.TickStyle, axis.MajorTickSize, out y0, out y1);
126.114 +
126.115 + foreach (double xValue in this.MajorTickValues)
126.116 + {
126.117 + if (xValue < axis.ActualMinimum || xValue > axis.ActualMaximum)
126.118 + {
126.119 + continue;
126.120 + }
126.121 +
126.122 + var pts = new List<ScreenPoint>();
126.123 + for (double th = angleAxis.ActualMinimum;
126.124 + th <= angleAxis.ActualMaximum + angleAxis.MinorStep * 0.01;
126.125 + th += angleAxis.MinorStep * 0.1)
126.126 + {
126.127 + pts.Add(axis.Transform(xValue, th, angleAxis));
126.128 + }
126.129 +
126.130 + if (this.MajorPen != null)
126.131 + {
126.132 + this.rc.DrawLine(pts, this.MajorPen.Color, this.MajorPen.Thickness, this.MajorPen.DashArray);
126.133 + }
126.134 +
126.135 + // RenderGridline(x, y + y0, x, y + y1, majorTickPen);
126.136 + // var pt = new ScreenPoint(x, istop ? y + y1 - TICK_DIST : y + y1 + TICK_DIST);
126.137 + // string text = axis.FormatValue(xValue);
126.138 + // double h = rc.MeasureText(text, axis.Font, axis.FontSize, axis.FontWeight).Height;
126.139 + // rc.DrawText(pt, text, axis.LabelColor ?? plot.TextColor,
126.140 + // axis.Font, axis.FontSize, axis.FontWeight,
126.141 + // axis.Angle,
126.142 + // HorizontalAlignment.Center, istop ? VerticalAlignment.Bottom : VerticalAlignment.Top);
126.143 + // maxh = Math.Max(maxh, h);
126.144 + }
126.145 + }
126.146 +
126.147 + }
126.148 +}
126.149 \ No newline at end of file
127.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
127.2 +++ b/External/OxyPlot/OxyPlot/Render/MathRenderingExtensions.cs Sat Jun 08 16:53:22 2013 +0000
127.3 @@ -0,0 +1,347 @@
127.4 +// --------------------------------------------------------------------------------------------------------------------
127.5 +// <copyright file="MathRenderingExtensions.cs" company="OxyPlot">
127.6 +// The MIT License (MIT)
127.7 +//
127.8 +// Copyright (c) 2012 Oystein Bjorke
127.9 +//
127.10 +// Permission is hereby granted, free of charge, to any person obtaining a
127.11 +// copy of this software and associated documentation files (the
127.12 +// "Software"), to deal in the Software without restriction, including
127.13 +// without limitation the rights to use, copy, modify, merge, publish,
127.14 +// distribute, sublicense, and/or sell copies of the Software, and to
127.15 +// permit persons to whom the Software is furnished to do so, subject to
127.16 +// the following conditions:
127.17 +//
127.18 +// The above copyright notice and this permission notice shall be included
127.19 +// in all copies or substantial portions of the Software.
127.20 +//
127.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
127.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
127.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
127.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
127.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
127.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
127.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
127.28 +// </copyright>
127.29 +// <summary>
127.30 +// The math rendering extensions.
127.31 +// </summary>
127.32 +// --------------------------------------------------------------------------------------------------------------------
127.33 +namespace OxyPlot
127.34 +{
127.35 + using System;
127.36 +
127.37 + /// <summary>
127.38 + /// Provides functionality to render mathematic expressions (TeX syntax).
127.39 + /// </summary>
127.40 + public static class MathRenderingExtensions
127.41 + {
127.42 + /// <summary>
127.43 + /// Initializes static members of the <see cref = "MathRenderingExtensions" /> class.
127.44 + /// </summary>
127.45 + static MathRenderingExtensions()
127.46 + {
127.47 + SubAlignment = 0.6;
127.48 + SubSize = 0.62;
127.49 + SuperAlignment = 0;
127.50 + SuperSize = 0.62;
127.51 + }
127.52 +
127.53 + /// <summary>
127.54 + /// Gets or sets the subscript alignment.
127.55 + /// </summary>
127.56 + private static double SubAlignment { get; set; }
127.57 +
127.58 + /// <summary>
127.59 + /// Gets or sets the subscript size.
127.60 + /// </summary>
127.61 + private static double SubSize { get; set; }
127.62 +
127.63 + /// <summary>
127.64 + /// Gets or sets the superscript alignment.
127.65 + /// </summary>
127.66 + private static double SuperAlignment { get; set; }
127.67 +
127.68 + /// <summary>
127.69 + /// Gets or sets the superscript size.
127.70 + /// </summary>
127.71 + private static double SuperSize { get; set; }
127.72 +
127.73 + /// <summary>
127.74 + /// Draws or measures text containing sub- and superscript.
127.75 + /// </summary>
127.76 + /// <param name="rc">The render context.</param>
127.77 + /// <param name="pt">The point.</param>
127.78 + /// <param name="text">The text.</param>
127.79 + /// <param name="textColor">Color of the text.</param>
127.80 + /// <param name="fontFamily">The font family.</param>
127.81 + /// <param name="fontSize">The font size.</param>
127.82 + /// <param name="fontWeight">The font weight.</param>
127.83 + /// <param name="angle">The angle.</param>
127.84 + /// <param name="ha">The horizontal alignment.</param>
127.85 + /// <param name="va">The vertical alignment.</param>
127.86 + /// <param name="maxsize">The maximum size of the text.</param>
127.87 + /// <param name="measure">Measure the size of the text if set to <c>true</c>.</param>
127.88 + /// <returns>The size of the text.</returns>
127.89 + /// <example>
127.90 + /// Subscript: H_{2}O
127.91 + /// Superscript: E=mc^{2}
127.92 + /// Both: A^{2}_{i,j}
127.93 + /// </example>
127.94 + public static OxySize DrawMathText(
127.95 + this IRenderContext rc,
127.96 + ScreenPoint pt,
127.97 + string text,
127.98 + OxyColor textColor,
127.99 + string fontFamily,
127.100 + double fontSize,
127.101 + double fontWeight,
127.102 + double angle,
127.103 + HorizontalAlignment ha,
127.104 + VerticalAlignment va,
127.105 + OxySize? maxsize,
127.106 + bool measure)
127.107 + {
127.108 + if (string.IsNullOrEmpty(text))
127.109 + {
127.110 + return OxySize.Empty;
127.111 + }
127.112 +
127.113 + if (angle.Equals(0) && (text.Contains("^{") || text.Contains("_{")))
127.114 + {
127.115 + double x = pt.X;
127.116 + double y = pt.Y;
127.117 +
127.118 + // Measure
127.119 + var size = InternalDrawMathText(rc, x, y, text, textColor, fontFamily, fontSize, fontWeight, true);
127.120 +
127.121 + switch (ha)
127.122 + {
127.123 + case HorizontalAlignment.Right:
127.124 + x -= size.Width;
127.125 + break;
127.126 + case HorizontalAlignment.Center:
127.127 + x -= size.Width * 0.5;
127.128 + break;
127.129 + }
127.130 +
127.131 + switch (va)
127.132 + {
127.133 + case VerticalAlignment.Bottom:
127.134 + y -= size.Height;
127.135 + break;
127.136 + case VerticalAlignment.Middle:
127.137 + y -= size.Height * 0.5;
127.138 + break;
127.139 + }
127.140 +
127.141 + InternalDrawMathText(rc, x, y, text, textColor, fontFamily, fontSize, fontWeight, false);
127.142 + return measure ? size : OxySize.Empty;
127.143 + }
127.144 +
127.145 + rc.DrawText(pt, text, textColor, fontFamily, fontSize, fontWeight, angle, ha, va, maxsize);
127.146 + if (measure)
127.147 + {
127.148 + return rc.MeasureText(text, fontFamily, fontSize, fontWeight);
127.149 + }
127.150 +
127.151 + return OxySize.Empty;
127.152 + }
127.153 +
127.154 + /// <summary>
127.155 + /// Draws text containing sub- and superscript.
127.156 + /// </summary>
127.157 + /// <param name="rc">The render context.</param>
127.158 + /// <param name="pt">The point.</param>
127.159 + /// <param name="text">The text.</param>
127.160 + /// <param name="textColor">Color of the text.</param>
127.161 + /// <param name="fontFamily">The font family.</param>
127.162 + /// <param name="fontSize">The font size.</param>
127.163 + /// <param name="fontWeight">The font weight.</param>
127.164 + /// <param name="angle">The angle.</param>
127.165 + /// <param name="ha">The horizontal alignment.</param>
127.166 + /// <param name="va">The vertical alignment.</param>
127.167 + /// <param name="maxsize">The maximum size of the text.</param>
127.168 + /// <example>
127.169 + /// Subscript: H_{2}O
127.170 + /// Superscript: E=mc^{2}
127.171 + /// Both: A^{2}_{i,j}
127.172 + /// </example>
127.173 + public static void DrawMathText(
127.174 + this IRenderContext rc,
127.175 + ScreenPoint pt,
127.176 + string text,
127.177 + OxyColor textColor,
127.178 + string fontFamily,
127.179 + double fontSize,
127.180 + double fontWeight,
127.181 + double angle,
127.182 + HorizontalAlignment ha,
127.183 + VerticalAlignment va,
127.184 + OxySize? maxsize = null)
127.185 + {
127.186 + DrawMathText(rc, pt, text, textColor, fontFamily, fontSize, fontWeight, angle, ha, va, maxsize, false);
127.187 + }
127.188 +
127.189 + /// <summary>
127.190 + /// The measure math text.
127.191 + /// </summary>
127.192 + /// <param name="rc">
127.193 + /// The render context.
127.194 + /// </param>
127.195 + /// <param name="text">
127.196 + /// The text.
127.197 + /// </param>
127.198 + /// <param name="fontFamily">
127.199 + /// The font family.
127.200 + /// </param>
127.201 + /// <param name="fontSize">
127.202 + /// The font size.
127.203 + /// </param>
127.204 + /// <param name="fontWeight">
127.205 + /// The font weight.
127.206 + /// </param>
127.207 + /// <returns>
127.208 + /// The size of the text.
127.209 + /// </returns>
127.210 + public static OxySize MeasureMathText(
127.211 + this IRenderContext rc, string text, string fontFamily, double fontSize, double fontWeight)
127.212 + {
127.213 + if (text.Contains("^{") || text.Contains("_{"))
127.214 + {
127.215 + return InternalDrawMathText(rc, 0, 0, text, null, fontFamily, fontSize, fontWeight, true);
127.216 + }
127.217 +
127.218 + return rc.MeasureText(text, fontFamily, fontSize, fontWeight);
127.219 + }
127.220 +
127.221 + /// <summary>
127.222 + /// The internal draw math text.
127.223 + /// </summary>
127.224 + /// <param name="rc">
127.225 + /// The render context.
127.226 + /// </param>
127.227 + /// <param name="x">
127.228 + /// The x.
127.229 + /// </param>
127.230 + /// <param name="y">
127.231 + /// The y.
127.232 + /// </param>
127.233 + /// <param name="s">
127.234 + /// The s.
127.235 + /// </param>
127.236 + /// <param name="textColor">
127.237 + /// The text color.
127.238 + /// </param>
127.239 + /// <param name="fontFamily">
127.240 + /// The font family.
127.241 + /// </param>
127.242 + /// <param name="fontSize">
127.243 + /// The font size.
127.244 + /// </param>
127.245 + /// <param name="fontWeight">
127.246 + /// The font weight.
127.247 + /// </param>
127.248 + /// <param name="measureOnly">
127.249 + /// The measure only.
127.250 + /// </param>
127.251 + /// <returns>
127.252 + /// The size of the text.
127.253 + /// </returns>
127.254 + private static OxySize InternalDrawMathText(
127.255 + IRenderContext rc,
127.256 + double x,
127.257 + double y,
127.258 + string s,
127.259 + OxyColor textColor,
127.260 + string fontFamily,
127.261 + double fontSize,
127.262 + double fontWeight,
127.263 + bool measureOnly)
127.264 + {
127.265 + int i = 0;
127.266 +
127.267 + double currentX = x;
127.268 + double maximumX = x;
127.269 + double maxHeight = 0;
127.270 +
127.271 + // http://en.wikipedia.org/wiki/Subscript_and_superscript
127.272 + double superscriptY = y + fontSize * SuperAlignment;
127.273 + double superscriptFontSize = fontSize * SuperSize;
127.274 + double subscriptY = y + fontSize * SubAlignment;
127.275 + double subscriptFontSize = fontSize * SubSize;
127.276 +
127.277 + Func<double, double, string, double, OxySize> drawText = (xb, yb, text, fSize) =>
127.278 + {
127.279 + if (!measureOnly)
127.280 + {
127.281 + rc.DrawText(new ScreenPoint(xb, yb), text, textColor, fontFamily, fSize, fontWeight);
127.282 + }
127.283 +
127.284 + return rc.MeasureText(text, fontFamily, fSize, fontWeight);
127.285 + };
127.286 +
127.287 + while (i < s.Length)
127.288 + {
127.289 + // Superscript
127.290 + if (i + 1 < s.Length && s[i] == '^' && s[i + 1] == '{')
127.291 + {
127.292 + int i1 = s.IndexOf('}', i);
127.293 + if (i1 != -1)
127.294 + {
127.295 + string supString = s.Substring(i + 2, i1 - i - 2);
127.296 + i = i1 + 1;
127.297 + OxySize size = drawText(currentX, superscriptY, supString, superscriptFontSize);
127.298 + if (currentX + size.Width > maximumX)
127.299 + {
127.300 + maximumX = currentX + size.Width;
127.301 + }
127.302 +
127.303 + continue;
127.304 + }
127.305 + }
127.306 +
127.307 + // Subscript
127.308 + if (i + 1 < s.Length && s[i] == '_' && s[i + 1] == '{')
127.309 + {
127.310 + int i1 = s.IndexOf('}', i);
127.311 + if (i1 != -1)
127.312 + {
127.313 + string subString = s.Substring(i + 2, i1 - i - 2);
127.314 + i = i1 + 1;
127.315 + OxySize size = drawText(currentX, subscriptY, subString, subscriptFontSize);
127.316 + if (currentX + size.Width > maximumX)
127.317 + {
127.318 + maximumX = currentX + size.Width;
127.319 + }
127.320 +
127.321 + continue;
127.322 + }
127.323 + }
127.324 +
127.325 + // Regular text
127.326 + int i2 = s.IndexOfAny("^_".ToCharArray(), i);
127.327 + string regularString;
127.328 + if (i2 == -1)
127.329 + {
127.330 + regularString = s.Substring(i);
127.331 + i = s.Length;
127.332 + }
127.333 + else
127.334 + {
127.335 + regularString = s.Substring(i, i2 - i);
127.336 + i = i2;
127.337 + }
127.338 +
127.339 + currentX = maximumX + 2;
127.340 + OxySize size2 = drawText(currentX, y, regularString, fontSize);
127.341 + currentX += size2.Width + 2;
127.342 + maxHeight = Math.Max(maxHeight, size2.Height);
127.343 + maximumX = currentX;
127.344 + }
127.345 +
127.346 + return new OxySize(maximumX - x, maxHeight);
127.347 + }
127.348 +
127.349 + }
127.350 +}
127.351 \ No newline at end of file
128.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
128.2 +++ b/External/OxyPlot/OxyPlot/Render/PlotRenderer.cs Sat Jun 08 16:53:22 2013 +0000
128.3 @@ -0,0 +1,159 @@
128.4 +// --------------------------------------------------------------------------------------------------------------------
128.5 +// <copyright file="PlotRenderer.cs" company="OxyPlot">
128.6 +// The MIT License (MIT)
128.7 +//
128.8 +// Copyright (c) 2012 Oystein Bjorke
128.9 +//
128.10 +// Permission is hereby granted, free of charge, to any person obtaining a
128.11 +// copy of this software and associated documentation files (the
128.12 +// "Software"), to deal in the Software without restriction, including
128.13 +// without limitation the rights to use, copy, modify, merge, publish,
128.14 +// distribute, sublicense, and/or sell copies of the Software, and to
128.15 +// permit persons to whom the Software is furnished to do so, subject to
128.16 +// the following conditions:
128.17 +//
128.18 +// The above copyright notice and this permission notice shall be included
128.19 +// in all copies or substantial portions of the Software.
128.20 +//
128.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
128.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
128.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
128.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
128.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
128.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
128.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
128.28 +// </copyright>
128.29 +// --------------------------------------------------------------------------------------------------------------------
128.30 +using System;
128.31 +
128.32 +namespace OxyPlot
128.33 +{
128.34 + public class PlotRenderer
128.35 + {
128.36 + protected readonly PlotModel plot;
128.37 + protected readonly IRenderContext rc;
128.38 +
128.39 + public PlotRenderer(IRenderContext rc, PlotModel p)
128.40 + {
128.41 + this.rc = rc;
128.42 + plot = p;
128.43 + }
128.44 +
128.45 + public void RenderTitle(string title, string subtitle)
128.46 + {
128.47 + OxySize size1 = rc.MeasureText(title, plot.TitleFont, plot.TitleFontSize, plot.TitleFontWeight);
128.48 + OxySize size2 = rc.MeasureText(subtitle, plot.TitleFont, plot.TitleFontSize, plot.TitleFontWeight);
128.49 + double height = size1.Height + size2.Height;
128.50 + double dy = (plot.AxisMargins.Top - height) * 0.5;
128.51 + double dx = (plot.Bounds.Left + plot.Bounds.Right) * 0.5;
128.52 +
128.53 + if (!String.IsNullOrEmpty(title))
128.54 + rc.DrawText(
128.55 + new ScreenPoint(dx, dy), title, plot.TextColor,
128.56 + plot.TitleFont, plot.TitleFontSize, plot.TitleFontWeight,
128.57 + 0,
128.58 + HorizontalTextAlign.Center, VerticalTextAlign.Top);
128.59 + if (!String.IsNullOrEmpty(subtitle))
128.60 + rc.DrawText(new ScreenPoint(dx, dy + size1.Height), subtitle, plot.TextColor,
128.61 + plot.TitleFont, plot.SubtitleFontSize, plot.SubtitleFontWeight, 0,
128.62 + HorizontalTextAlign.Center, VerticalTextAlign.Top);
128.63 + }
128.64 +
128.65 + public void RenderRect(OxyRect bounds, OxyColor fill, OxyColor borderColor, double borderThickness)
128.66 + {
128.67 + var border = new[]
128.68 + {
128.69 + new ScreenPoint(bounds.Left, bounds.Top), new ScreenPoint(bounds.Right, bounds.Top),
128.70 + new ScreenPoint(bounds.Right, bounds.Bottom), new ScreenPoint(bounds.Left, bounds.Bottom),
128.71 + new ScreenPoint(bounds.Left, bounds.Top)
128.72 + };
128.73 +
128.74 + rc.DrawPolygon(border, fill, borderColor, borderThickness, null, true);
128.75 + }
128.76 +
128.77 + private static readonly double LEGEND_PADDING = 8;
128.78 +
128.79 + public void RenderLegends()
128.80 + {
128.81 + double maxWidth = 0;
128.82 + double maxHeight = 0;
128.83 + double totalHeight = 0;
128.84 +
128.85 + // Measure
128.86 + foreach (var s in plot.Series)
128.87 + {
128.88 + if (String.IsNullOrEmpty(s.Title))
128.89 + continue;
128.90 + var oxySize = rc.MeasureText(s.Title, plot.LegendFont, plot.LegendFontSize);
128.91 + if (oxySize.Width > maxWidth) maxWidth = oxySize.Width;
128.92 + if (oxySize.Height > maxHeight) maxHeight = oxySize.Height;
128.93 + totalHeight += oxySize.Height;
128.94 + }
128.95 +
128.96 + double lineLength = plot.LegendSymbolLength;
128.97 +
128.98 + // Arrange
128.99 + double x0 = double.NaN, x1 = double.NaN, y0 = double.NaN;
128.100 +
128.101 + // padding padding
128.102 + // lineLength
128.103 + // y0 -----o---- seriesName
128.104 + // x0 x1
128.105 +
128.106 + double sign = 1;
128.107 + if (plot.IsLegendOutsidePlotArea)
128.108 + sign = -1;
128.109 +
128.110 + // Horizontal alignment
128.111 + HorizontalTextAlign ha = HorizontalTextAlign.Left;
128.112 + switch (plot.LegendPosition)
128.113 + {
128.114 + case LegendPosition.TopRight:
128.115 + case LegendPosition.BottomRight:
128.116 + x0 = plot.Bounds.Right - LEGEND_PADDING * sign;
128.117 + x1 = x0 - lineLength * sign - LEGEND_PADDING * sign;
128.118 + ha = sign == 1 ? HorizontalTextAlign.Right : HorizontalTextAlign.Left;
128.119 + break;
128.120 + case LegendPosition.TopLeft:
128.121 + case LegendPosition.BottomLeft:
128.122 + x0 = plot.Bounds.Left + LEGEND_PADDING * sign;
128.123 + x1 = x0 + lineLength * sign + LEGEND_PADDING * sign;
128.124 + ha = sign == 1 ? HorizontalTextAlign.Left : HorizontalTextAlign.Right;
128.125 + break;
128.126 + }
128.127 +
128.128 + // Vertical alignment
128.129 + VerticalTextAlign va = VerticalTextAlign.Middle;
128.130 + switch (plot.LegendPosition)
128.131 + {
128.132 + case LegendPosition.TopRight:
128.133 + case LegendPosition.TopLeft:
128.134 + y0 = plot.Bounds.Top + LEGEND_PADDING + maxHeight / 2;
128.135 + break;
128.136 + case LegendPosition.BottomRight:
128.137 + case LegendPosition.BottomLeft:
128.138 + y0 = plot.Bounds.Bottom - maxHeight + LEGEND_PADDING;
128.139 + break;
128.140 + }
128.141 +
128.142 + foreach (var s in plot.Series)
128.143 + {
128.144 + if (String.IsNullOrEmpty(s.Title))
128.145 + continue;
128.146 + rc.DrawText(new ScreenPoint(x1, y0),
128.147 + s.Title, plot.TextColor,
128.148 + plot.LegendFont, plot.LegendFontSize, 500, 0,
128.149 + ha, va);
128.150 + OxyRect rect = new OxyRect(x0 - lineLength, y0 - maxHeight / 2, lineLength, maxHeight);
128.151 + if (ha == HorizontalTextAlign.Left)
128.152 + rect = new OxyRect(x0, y0 - maxHeight / 2, lineLength, maxHeight);
128.153 +
128.154 + s.RenderLegend(rc, rect);
128.155 + if (plot.LegendPosition == LegendPosition.TopLeft || plot.LegendPosition == LegendPosition.TopRight)
128.156 + y0 += maxHeight;
128.157 + else
128.158 + y0 -= maxHeight;
128.159 + }
128.160 + }
128.161 + }
128.162 +}
128.163 \ No newline at end of file
129.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
129.2 +++ b/External/OxyPlot/OxyPlot/Render/RenderContextBase.cs Sat Jun 08 16:53:22 2013 +0000
129.3 @@ -0,0 +1,423 @@
129.4 +// --------------------------------------------------------------------------------------------------------------------
129.5 +// <copyright file="RenderContextBase.cs" company="OxyPlot">
129.6 +// The MIT License (MIT)
129.7 +//
129.8 +// Copyright (c) 2012 Oystein Bjorke
129.9 +//
129.10 +// Permission is hereby granted, free of charge, to any person obtaining a
129.11 +// copy of this software and associated documentation files (the
129.12 +// "Software"), to deal in the Software without restriction, including
129.13 +// without limitation the rights to use, copy, modify, merge, publish,
129.14 +// distribute, sublicense, and/or sell copies of the Software, and to
129.15 +// permit persons to whom the Software is furnished to do so, subject to
129.16 +// the following conditions:
129.17 +//
129.18 +// The above copyright notice and this permission notice shall be included
129.19 +// in all copies or substantial portions of the Software.
129.20 +//
129.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
129.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
129.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
129.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
129.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
129.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
129.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
129.28 +// </copyright>
129.29 +// <summary>
129.30 +// The abstract render context base class.
129.31 +// </summary>
129.32 +// --------------------------------------------------------------------------------------------------------------------
129.33 +namespace OxyPlot
129.34 +{
129.35 + using System.Collections.Generic;
129.36 +
129.37 + /// <summary>
129.38 + /// Provides an abstract base class for rendering contexts.
129.39 + /// </summary>
129.40 + public abstract class RenderContextBase : IRenderContext
129.41 + {
129.42 + /// <summary>
129.43 + /// Initializes a new instance of the <see cref="RenderContextBase" /> class.
129.44 + /// </summary>
129.45 + protected RenderContextBase()
129.46 + {
129.47 + this.RendersToScreen = true;
129.48 + }
129.49 +
129.50 + /// <summary>
129.51 + /// Gets or sets a value indicating whether the context renders to screen.
129.52 + /// </summary>
129.53 + /// <value>
129.54 + /// <c>true</c> if the context renders to screen; otherwise, <c>false</c>.
129.55 + /// </value>
129.56 + public bool RendersToScreen { get; set; }
129.57 +
129.58 + /// <summary>
129.59 + /// Draws an ellipse.
129.60 + /// </summary>
129.61 + /// <param name="rect">
129.62 + /// The rectangle.
129.63 + /// </param>
129.64 + /// <param name="fill">
129.65 + /// The fill color.
129.66 + /// </param>
129.67 + /// <param name="stroke">
129.68 + /// The stroke color.
129.69 + /// </param>
129.70 + /// <param name="thickness">
129.71 + /// The thickness.
129.72 + /// </param>
129.73 + public abstract void DrawEllipse(OxyRect rect, OxyColor fill, OxyColor stroke, double thickness);
129.74 +
129.75 + /// <summary>
129.76 + /// Draws the collection of ellipses, where all have the same stroke and fill.
129.77 + /// This performs better than calling DrawEllipse multiple times.
129.78 + /// </summary>
129.79 + /// <param name="rectangles">
129.80 + /// The rectangles.
129.81 + /// </param>
129.82 + /// <param name="fill">
129.83 + /// The fill color.
129.84 + /// </param>
129.85 + /// <param name="stroke">
129.86 + /// The stroke color.
129.87 + /// </param>
129.88 + /// <param name="thickness">
129.89 + /// The stroke thickness.
129.90 + /// </param>
129.91 + public virtual void DrawEllipses(IList<OxyRect> rectangles, OxyColor fill, OxyColor stroke, double thickness)
129.92 + {
129.93 + foreach (var r in rectangles)
129.94 + {
129.95 + this.DrawEllipse(r, fill, stroke, thickness);
129.96 + }
129.97 + }
129.98 +
129.99 + /// <summary>
129.100 + /// Draws the polyline from the specified points.
129.101 + /// </summary>
129.102 + /// <param name="points">
129.103 + /// The points.
129.104 + /// </param>
129.105 + /// <param name="stroke">
129.106 + /// The stroke color.
129.107 + /// </param>
129.108 + /// <param name="thickness">
129.109 + /// The stroke thickness.
129.110 + /// </param>
129.111 + /// <param name="dashArray">
129.112 + /// The dash array.
129.113 + /// </param>
129.114 + /// <param name="lineJoin">
129.115 + /// The line join type.
129.116 + /// </param>
129.117 + /// <param name="aliased">
129.118 + /// if set to <c>true</c> the shape will be aliased.
129.119 + /// </param>
129.120 + public abstract void DrawLine(
129.121 + IList<ScreenPoint> points,
129.122 + OxyColor stroke,
129.123 + double thickness,
129.124 + double[] dashArray,
129.125 + OxyPenLineJoin lineJoin,
129.126 + bool aliased);
129.127 +
129.128 + /// <summary>
129.129 + /// Draws the multiple line segments defined by points (0,1) (2,3) (4,5) etc.
129.130 + /// This should have better performance than calling DrawLine for each segment.
129.131 + /// </summary>
129.132 + /// <param name="points">
129.133 + /// The points.
129.134 + /// </param>
129.135 + /// <param name="stroke">
129.136 + /// The stroke color.
129.137 + /// </param>
129.138 + /// <param name="thickness">
129.139 + /// The stroke thickness.
129.140 + /// </param>
129.141 + /// <param name="dashArray">
129.142 + /// The dash array.
129.143 + /// </param>
129.144 + /// <param name="lineJoin">
129.145 + /// The line join type.
129.146 + /// </param>
129.147 + /// <param name="aliased">
129.148 + /// if set to <c>true</c> the shape will be aliased.
129.149 + /// </param>
129.150 + public virtual void DrawLineSegments(
129.151 + IList<ScreenPoint> points,
129.152 + OxyColor stroke,
129.153 + double thickness,
129.154 + double[] dashArray,
129.155 + OxyPenLineJoin lineJoin,
129.156 + bool aliased)
129.157 + {
129.158 + for (int i = 0; i + 1 < points.Count; i += 2)
129.159 + {
129.160 + this.DrawLine(new[] { points[i], points[i + 1] }, stroke, thickness, dashArray, lineJoin, aliased);
129.161 + }
129.162 + }
129.163 +
129.164 + /// <summary>
129.165 + /// Draws the polygon from the specified points. The polygon can have stroke and/or fill.
129.166 + /// </summary>
129.167 + /// <param name="points">
129.168 + /// The points.
129.169 + /// </param>
129.170 + /// <param name="fill">
129.171 + /// The fill color.
129.172 + /// </param>
129.173 + /// <param name="stroke">
129.174 + /// The stroke color.
129.175 + /// </param>
129.176 + /// <param name="thickness">
129.177 + /// The stroke thickness.
129.178 + /// </param>
129.179 + /// <param name="dashArray">
129.180 + /// The dash array.
129.181 + /// </param>
129.182 + /// <param name="lineJoin">
129.183 + /// The line join type.
129.184 + /// </param>
129.185 + /// <param name="aliased">
129.186 + /// if set to <c>true</c> the shape will be aliased.
129.187 + /// </param>
129.188 + public abstract void DrawPolygon(
129.189 + IList<ScreenPoint> points,
129.190 + OxyColor fill,
129.191 + OxyColor stroke,
129.192 + double thickness,
129.193 + double[] dashArray,
129.194 + OxyPenLineJoin lineJoin,
129.195 + bool aliased);
129.196 +
129.197 + /// <summary>
129.198 + /// Draws a collection of polygons, where all polygons have the same stroke and fill.
129.199 + /// This performs better than calling DrawPolygon multiple times.
129.200 + /// </summary>
129.201 + /// <param name="polygons">
129.202 + /// The polygons.
129.203 + /// </param>
129.204 + /// <param name="fill">
129.205 + /// The fill color.
129.206 + /// </param>
129.207 + /// <param name="stroke">
129.208 + /// The stroke color.
129.209 + /// </param>
129.210 + /// <param name="thickness">
129.211 + /// The stroke thickness.
129.212 + /// </param>
129.213 + /// <param name="dashArray">
129.214 + /// The dash array.
129.215 + /// </param>
129.216 + /// <param name="lineJoin">
129.217 + /// The line join type.
129.218 + /// </param>
129.219 + /// <param name="aliased">
129.220 + /// if set to <c>true</c> the shape will be aliased.
129.221 + /// </param>
129.222 + public virtual void DrawPolygons(
129.223 + IList<IList<ScreenPoint>> polygons,
129.224 + OxyColor fill,
129.225 + OxyColor stroke,
129.226 + double thickness,
129.227 + double[] dashArray,
129.228 + OxyPenLineJoin lineJoin,
129.229 + bool aliased)
129.230 + {
129.231 + foreach (var polygon in polygons)
129.232 + {
129.233 + this.DrawPolygon(polygon, fill, stroke, thickness, dashArray, lineJoin, aliased);
129.234 + }
129.235 + }
129.236 +
129.237 + /// <summary>
129.238 + /// Draws the rectangle.
129.239 + /// </summary>
129.240 + /// <param name="rect">
129.241 + /// The rectangle.
129.242 + /// </param>
129.243 + /// <param name="fill">
129.244 + /// The fill color.
129.245 + /// </param>
129.246 + /// <param name="stroke">
129.247 + /// The stroke color.
129.248 + /// </param>
129.249 + /// <param name="thickness">
129.250 + /// The stroke thickness.
129.251 + /// </param>
129.252 + public abstract void DrawRectangle(OxyRect rect, OxyColor fill, OxyColor stroke, double thickness);
129.253 +
129.254 + /// <summary>
129.255 + /// Draws a collection of rectangles, where all have the same stroke and fill.
129.256 + /// This performs better than calling DrawRectangle multiple times.
129.257 + /// </summary>
129.258 + /// <param name="rectangles">
129.259 + /// The rectangles.
129.260 + /// </param>
129.261 + /// <param name="fill">
129.262 + /// The fill color.
129.263 + /// </param>
129.264 + /// <param name="stroke">
129.265 + /// The stroke color.
129.266 + /// </param>
129.267 + /// <param name="thickness">
129.268 + /// The stroke thickness.
129.269 + /// </param>
129.270 + public virtual void DrawRectangles(IList<OxyRect> rectangles, OxyColor fill, OxyColor stroke, double thickness)
129.271 + {
129.272 + foreach (var r in rectangles)
129.273 + {
129.274 + this.DrawRectangle(r, fill, stroke, thickness);
129.275 + }
129.276 + }
129.277 +
129.278 + /// <summary>
129.279 + /// Draws the text.
129.280 + /// </summary>
129.281 + /// <param name="p">
129.282 + /// The p.
129.283 + /// </param>
129.284 + /// <param name="text">
129.285 + /// The text.
129.286 + /// </param>
129.287 + /// <param name="fill">
129.288 + /// The fill color.
129.289 + /// </param>
129.290 + /// <param name="fontFamily">
129.291 + /// The font family.
129.292 + /// </param>
129.293 + /// <param name="fontSize">
129.294 + /// Size of the font.
129.295 + /// </param>
129.296 + /// <param name="fontWeight">
129.297 + /// The font weight.
129.298 + /// </param>
129.299 + /// <param name="rotate">
129.300 + /// The rotation angle.
129.301 + /// </param>
129.302 + /// <param name="halign">
129.303 + /// The horizontal alignment.
129.304 + /// </param>
129.305 + /// <param name="valign">
129.306 + /// The vertical alignment.
129.307 + /// </param>
129.308 + /// <param name="maxSize">
129.309 + /// The maximum size of the text.
129.310 + /// </param>
129.311 + public abstract void DrawText(
129.312 + ScreenPoint p,
129.313 + string text,
129.314 + OxyColor fill,
129.315 + string fontFamily,
129.316 + double fontSize,
129.317 + double fontWeight,
129.318 + double rotate,
129.319 + HorizontalAlignment halign,
129.320 + VerticalAlignment valign,
129.321 + OxySize? maxSize);
129.322 +
129.323 + /// <summary>
129.324 + /// Measures the text.
129.325 + /// </summary>
129.326 + /// <param name="text">
129.327 + /// The text.
129.328 + /// </param>
129.329 + /// <param name="fontFamily">
129.330 + /// The font family.
129.331 + /// </param>
129.332 + /// <param name="fontSize">
129.333 + /// Size of the font.
129.334 + /// </param>
129.335 + /// <param name="fontWeight">
129.336 + /// The font weight.
129.337 + /// </param>
129.338 + /// <returns>
129.339 + /// The text size.
129.340 + /// </returns>
129.341 + public abstract OxySize MeasureText(string text, string fontFamily, double fontSize, double fontWeight);
129.342 +
129.343 + /// <summary>
129.344 + /// Sets the tool tip for the following items.
129.345 + /// </summary>
129.346 + /// <param name="text">
129.347 + /// The text in the tooltip.
129.348 + /// </param>
129.349 + /// <params>
129.350 + /// This is only used in the plot controls.
129.351 + /// </params>
129.352 + public virtual void SetToolTip(string text)
129.353 + {
129.354 + }
129.355 +
129.356 + /// <summary>
129.357 + /// Cleans up resources not in use.
129.358 + /// </summary>
129.359 + /// <remarks>
129.360 + /// This method is called at the end of each rendering.
129.361 + /// </remarks>
129.362 + public virtual void CleanUp()
129.363 + {
129.364 + }
129.365 +
129.366 + /// <summary>
129.367 + /// Gets the size of the specified image.
129.368 + /// </summary>
129.369 + /// <param name="source">The image source.</param>
129.370 + /// <returns>
129.371 + /// The image info.
129.372 + /// </returns>
129.373 + public virtual OxyImageInfo GetImageInfo(OxyImage source)
129.374 + {
129.375 + return null;
129.376 + }
129.377 +
129.378 + /// <summary>
129.379 + /// Draws the image.
129.380 + /// </summary>
129.381 + /// <param name="source">The source.</param>
129.382 + /// <param name="srcX">The SRC X.</param>
129.383 + /// <param name="srcY">The SRC Y.</param>
129.384 + /// <param name="srcWidth">Width of the SRC.</param>
129.385 + /// <param name="srcHeight">Height of the SRC.</param>
129.386 + /// <param name="x">The x.</param>
129.387 + /// <param name="y">The y.</param>
129.388 + /// <param name="w">The w.</param>
129.389 + /// <param name="h">The h.</param>
129.390 + /// <param name="opacity">The opacity.</param>
129.391 + /// <param name="interpolate">interpolate if set to <c>true</c>.</param>
129.392 + public virtual void DrawImage(
129.393 + OxyImage source,
129.394 + uint srcX,
129.395 + uint srcY,
129.396 + uint srcWidth,
129.397 + uint srcHeight,
129.398 + double x,
129.399 + double y,
129.400 + double w,
129.401 + double h,
129.402 + double opacity,
129.403 + bool interpolate)
129.404 + {
129.405 + }
129.406 +
129.407 + /// <summary>
129.408 + /// Sets the clip rectangle.
129.409 + /// </summary>
129.410 + /// <param name="rect">The clip rectangle.</param>
129.411 + /// <returns>
129.412 + /// True if the clip rectangle was set.
129.413 + /// </returns>
129.414 + public virtual bool SetClip(OxyRect rect)
129.415 + {
129.416 + return false;
129.417 + }
129.418 +
129.419 + /// <summary>
129.420 + /// Resets the clip rectangle.
129.421 + /// </summary>
129.422 + public virtual void ResetClip()
129.423 + {
129.424 + }
129.425 + }
129.426 +}
129.427 \ No newline at end of file
130.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
130.2 +++ b/External/OxyPlot/OxyPlot/Render/RenderingExtensions.cs Sat Jun 08 16:53:22 2013 +0000
130.3 @@ -0,0 +1,1109 @@
130.4 +// --------------------------------------------------------------------------------------------------------------------
130.5 +// <copyright file="RenderingExtensions.cs" company="OxyPlot">
130.6 +// The MIT License (MIT)
130.7 +//
130.8 +// Copyright (c) 2012 Oystein Bjorke
130.9 +//
130.10 +// Permission is hereby granted, free of charge, to any person obtaining a
130.11 +// copy of this software and associated documentation files (the
130.12 +// "Software"), to deal in the Software without restriction, including
130.13 +// without limitation the rights to use, copy, modify, merge, publish,
130.14 +// distribute, sublicense, and/or sell copies of the Software, and to
130.15 +// permit persons to whom the Software is furnished to do so, subject to
130.16 +// the following conditions:
130.17 +//
130.18 +// The above copyright notice and this permission notice shall be included
130.19 +// in all copies or substantial portions of the Software.
130.20 +//
130.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
130.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
130.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
130.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
130.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
130.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
130.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
130.28 +// </copyright>
130.29 +// <summary>
130.30 +// The rendering extensions.
130.31 +// </summary>
130.32 +// --------------------------------------------------------------------------------------------------------------------
130.33 +
130.34 +namespace OxyPlot
130.35 +{
130.36 + using System;
130.37 + using System.Collections.Generic;
130.38 + using System.Linq;
130.39 +
130.40 + /// <summary>
130.41 + /// Provides extension methods for <see cref="IRenderContext"/>.
130.42 + /// </summary>
130.43 + public static class RenderingExtensions
130.44 + {
130.45 + /* Length constants used to draw triangles and stars
130.46 + ___
130.47 + /\ |
130.48 + / \ |
130.49 + / \ | M2
130.50 + / \ |
130.51 + / \ |
130.52 + / + \ ---
130.53 + / \ |
130.54 + / \ | M1
130.55 + /________________\ _|_
130.56 + |--------|-------|
130.57 + 1 1
130.58 +
130.59 + |
130.60 + \ | / ---
130.61 + \ | / | M3
130.62 + \ | / |
130.63 + ---------+-------- ---
130.64 + / | \ | M3
130.65 + / | \ |
130.66 + / | \ ---
130.67 + |
130.68 + |-----|-----|
130.69 + M3 M3
130.70 + */
130.71 +
130.72 + /// <summary>
130.73 + /// The vertical distance to the bottom points of the triangles.
130.74 + /// </summary>
130.75 + private static readonly double M1 = Math.Tan(Math.PI / 6);
130.76 +
130.77 + /// <summary>
130.78 + /// The vertical distance to the top points of the triangles .
130.79 + /// </summary>
130.80 + private static readonly double M2 = Math.Sqrt(1 + (M1 * M1));
130.81 +
130.82 + /// <summary>
130.83 + /// The horizontal/vertical distance to the end points of the stars.
130.84 + /// </summary>
130.85 + private static readonly double M3 = Math.Tan(Math.PI / 4);
130.86 +
130.87 + /// <summary>
130.88 + /// Draws the clipped line.
130.89 + /// </summary>
130.90 + /// <param name="rc">The render context.</param>
130.91 + /// <param name="points">The points.</param>
130.92 + /// <param name="clippingRectangle">The clipping rectangle.</param>
130.93 + /// <param name="minDistSquared">The squared minimum distance.</param>
130.94 + /// <param name="stroke">The stroke.</param>
130.95 + /// <param name="strokeThickness">The stroke thickness.</param>
130.96 + /// <param name="lineStyle">The line style.</param>
130.97 + /// <param name="lineJoin">The line join.</param>
130.98 + /// <param name="aliased">if set to <c>true</c> [aliased].</param>
130.99 + /// <param name="pointsRendered">The points rendered callback.</param>
130.100 + public static void DrawClippedLine(
130.101 + this IRenderContext rc,
130.102 + IList<ScreenPoint> points,
130.103 + OxyRect clippingRectangle,
130.104 + double minDistSquared,
130.105 + OxyColor stroke,
130.106 + double strokeThickness,
130.107 + LineStyle lineStyle,
130.108 + OxyPenLineJoin lineJoin,
130.109 + bool aliased,
130.110 + Action<IList<ScreenPoint>> pointsRendered = null)
130.111 + {
130.112 + var clipping = new CohenSutherlandClipping(clippingRectangle.Left, clippingRectangle.Right, clippingRectangle.Top, clippingRectangle.Bottom);
130.113 +
130.114 + var pts = new List<ScreenPoint>();
130.115 + int n = points.Count;
130.116 + if (n > 0)
130.117 + {
130.118 + if (n == 1)
130.119 + {
130.120 + pts.Add(points[0]);
130.121 + }
130.122 +
130.123 + var last = points[0];
130.124 + for (int i = 1; i < n; i++)
130.125 + {
130.126 + var s0 = points[i - 1];
130.127 + var s1 = points[i];
130.128 +
130.129 + // Clipped version of this and next point.
130.130 + var sc0 = s0;
130.131 + var sc1 = s1;
130.132 + bool isInside = clipping.ClipLine(ref sc0, ref sc1);
130.133 +
130.134 + if (!isInside)
130.135 + {
130.136 + // keep the previous coordinate
130.137 + continue;
130.138 + }
130.139 +
130.140 + // render from s0c-s1c
130.141 + double dx = sc1.x - last.x;
130.142 + double dy = sc1.y - last.y;
130.143 +
130.144 + if ((dx * dx) + (dy * dy) > minDistSquared || i == 1 || i == n - 1)
130.145 + {
130.146 + if (!sc0.Equals(last) || i == 1)
130.147 + {
130.148 + pts.Add(sc0);
130.149 + }
130.150 +
130.151 + pts.Add(sc1);
130.152 + last = sc1;
130.153 + }
130.154 +
130.155 + // render the line if we are leaving the clipping region););
130.156 + if (!clipping.IsInside(s1))
130.157 + {
130.158 + if (pts.Count > 0)
130.159 + {
130.160 + EnsureNonEmptyLineIsVisible(pts);
130.161 + rc.DrawLine(pts, stroke, strokeThickness, lineStyle.GetDashArray(), lineJoin, aliased);
130.162 + if (pointsRendered != null)
130.163 + {
130.164 + pointsRendered(pts);
130.165 + }
130.166 +
130.167 + pts = new List<ScreenPoint>();
130.168 + }
130.169 + }
130.170 + }
130.171 +
130.172 + if (pts.Count > 0)
130.173 + {
130.174 + EnsureNonEmptyLineIsVisible(pts);
130.175 + rc.DrawLine(pts, stroke, strokeThickness, lineStyle.GetDashArray(), lineJoin, aliased);
130.176 +
130.177 + // Execute the 'callback'.
130.178 + if (pointsRendered != null)
130.179 + {
130.180 + pointsRendered(pts);
130.181 + }
130.182 + }
130.183 + }
130.184 + }
130.185 +
130.186 + /// <summary>
130.187 + /// Draws the clipped line segments.
130.188 + /// </summary>
130.189 + /// <param name="rc">The render context.</param>
130.190 + /// <param name="points">The points.</param>
130.191 + /// <param name="clippingRectangle">The clipping rectangle.</param>
130.192 + /// <param name="stroke">The stroke.</param>
130.193 + /// <param name="strokeThickness">The stroke thickness.</param>
130.194 + /// <param name="lineStyle">The line style.</param>
130.195 + /// <param name="lineJoin">The line join.</param>
130.196 + /// <param name="aliased">if set to <c>true</c> [aliased].</param>
130.197 + public static void DrawClippedLineSegments(
130.198 + this IRenderContext rc,
130.199 + IList<ScreenPoint> points,
130.200 + OxyRect clippingRectangle,
130.201 + OxyColor stroke,
130.202 + double strokeThickness,
130.203 + LineStyle lineStyle,
130.204 + OxyPenLineJoin lineJoin,
130.205 + bool aliased)
130.206 + {
130.207 + if (rc.SetClip(clippingRectangle))
130.208 + {
130.209 + rc.DrawLineSegments(points, stroke, strokeThickness, lineStyle.GetDashArray(), lineJoin, aliased);
130.210 + rc.ResetClip();
130.211 + return;
130.212 + }
130.213 +
130.214 + var clipping = new CohenSutherlandClipping(clippingRectangle.Left, clippingRectangle.Right, clippingRectangle.Top, clippingRectangle.Bottom);
130.215 +
130.216 + var clippedPoints = new List<ScreenPoint>(points.Count);
130.217 + for (int i = 0; i + 1 < points.Count; i += 2)
130.218 + {
130.219 + var s0 = points[i];
130.220 + var s1 = points[i + 1];
130.221 + if (clipping.ClipLine(ref s0, ref s1))
130.222 + {
130.223 + clippedPoints.Add(s0);
130.224 + clippedPoints.Add(s1);
130.225 + }
130.226 + }
130.227 +
130.228 + rc.DrawLineSegments(clippedPoints, stroke, strokeThickness, lineStyle.GetDashArray(), lineJoin, aliased);
130.229 + }
130.230 +
130.231 + /// <summary>
130.232 + /// Draws the specified image.
130.233 + /// </summary>
130.234 + /// <param name="rc">The render context.</param>
130.235 + /// <param name="image">The image.</param>
130.236 + /// <param name="x">The destination X position.</param>
130.237 + /// <param name="y">The destination Y position.</param>
130.238 + /// <param name="w">The width.</param>
130.239 + /// <param name="h">The height.</param>
130.240 + /// <param name="opacity">The opacity.</param>
130.241 + /// <param name="interpolate">Interpolate the image if set to <c>true</c>.</param>
130.242 + public static void DrawImage(
130.243 + this IRenderContext rc,
130.244 + OxyImage image,
130.245 + double x,
130.246 + double y,
130.247 + double w,
130.248 + double h,
130.249 + double opacity,
130.250 + bool interpolate)
130.251 + {
130.252 + var info = rc.GetImageInfo(image);
130.253 + if (info == null)
130.254 + {
130.255 + return;
130.256 + }
130.257 +
130.258 + rc.DrawImage(image, 0, 0, info.Width, info.Height, x, y, w, h, opacity, interpolate);
130.259 + }
130.260 +
130.261 + /// <summary>
130.262 + /// Draws the clipped image.
130.263 + /// </summary>
130.264 + /// <param name="rc">The render context.</param>
130.265 + /// <param name="clippingRect">The clipping rectangle.</param>
130.266 + /// <param name="source">The source.</param>
130.267 + /// <param name="x">The destination X position.</param>
130.268 + /// <param name="y">The destination Y position.</param>
130.269 + /// <param name="w">The width.</param>
130.270 + /// <param name="h">The height.</param>
130.271 + /// <param name="opacity">The opacity.</param>
130.272 + /// <param name="interpolate">interpolate if set to <c>true</c>.</param>
130.273 + public static void DrawClippedImage(
130.274 + this IRenderContext rc,
130.275 + OxyRect clippingRect,
130.276 + OxyImage source,
130.277 + double x,
130.278 + double y,
130.279 + double w,
130.280 + double h,
130.281 + double opacity,
130.282 + bool interpolate)
130.283 + {
130.284 + if (x > clippingRect.Right || x + w < clippingRect.Left || y > clippingRect.Bottom || y + h < clippingRect.Top)
130.285 + {
130.286 + return;
130.287 + }
130.288 +
130.289 + if (rc.SetClip(clippingRect))
130.290 + {
130.291 + // The render context supports clipping, then we can draw the whole image
130.292 + rc.DrawImage(source, x, y, w, h, opacity, interpolate);
130.293 + rc.ResetClip();
130.294 + return;
130.295 + }
130.296 +
130.297 + // The render context does not support clipping, we must calculate the rectangle
130.298 + var info = rc.GetImageInfo(source);
130.299 + if (info == null)
130.300 + {
130.301 + return;
130.302 + }
130.303 +
130.304 + // Fint the positions of the clipping rectangle normalized to image coordinates (0,1)
130.305 + var i0 = (clippingRect.Left - x) / w;
130.306 + var i1 = (clippingRect.Right - x) / w;
130.307 + var j0 = (clippingRect.Top - y) / h;
130.308 + var j1 = (clippingRect.Bottom - y) / h;
130.309 +
130.310 + // Find the origin of the clipped source rectangle
130.311 + var srcx = i0 < 0 ? 0u : i0 * info.Width;
130.312 + var srcy = j0 < 0 ? 0u : j0 * info.Height;
130.313 + srcx = (int)Math.Ceiling(srcx);
130.314 + srcy = (int)Math.Ceiling(srcy);
130.315 +
130.316 + // Find the size of the clipped source rectangle
130.317 + var srcw = i1 > 1 ? info.Width - srcx : (i1 * info.Width) - srcx;
130.318 + var srch = j1 > 1 ? info.Height - srcy : (j1 * info.Height) - srcy;
130.319 + srcw = (int)srcw;
130.320 + srch = (int)srch;
130.321 +
130.322 + if ((int)srcw <= 0 || (int)srch <= 0)
130.323 + {
130.324 + return;
130.325 + }
130.326 +
130.327 + // The clipped destination rectangle
130.328 + var destx = i0 < 0 ? x : x + (srcx / info.Width * w);
130.329 + var desty = j0 < 0 ? y : y + (srcy / info.Height * h);
130.330 + var destw = w * srcw / info.Width;
130.331 + var desth = h * srch / info.Height;
130.332 +
130.333 + rc.DrawImage(source, (uint)srcx, (uint)srcy, (uint)srcw, (uint)srch, destx, desty, destw, desth, opacity, interpolate);
130.334 + }
130.335 +
130.336 + /// <summary>
130.337 + /// Draws the polygon within the specified clipping rectangle.
130.338 + /// </summary>
130.339 + /// <param name="rc">
130.340 + /// The render context.
130.341 + /// </param>
130.342 + /// <param name="points">
130.343 + /// The points.
130.344 + /// </param>
130.345 + /// <param name="clippingRectangle">
130.346 + /// The clipping rectangle.
130.347 + /// </param>
130.348 + /// <param name="minDistSquared">
130.349 + /// The squared minimum distance between points.
130.350 + /// </param>
130.351 + /// <param name="fill">
130.352 + /// The fill.
130.353 + /// </param>
130.354 + /// <param name="stroke">
130.355 + /// The stroke.
130.356 + /// </param>
130.357 + /// <param name="strokeThickness">
130.358 + /// The stroke thickness.
130.359 + /// </param>
130.360 + /// <param name="lineStyle">
130.361 + /// The line style.
130.362 + /// </param>
130.363 + /// <param name="lineJoin">
130.364 + /// The line join.
130.365 + /// </param>
130.366 + /// <param name="aliased">
130.367 + /// The aliased.
130.368 + /// </param>
130.369 + public static void DrawClippedPolygon(
130.370 + this IRenderContext rc,
130.371 + IList<ScreenPoint> points,
130.372 + OxyRect clippingRectangle,
130.373 + double minDistSquared,
130.374 + OxyColor fill,
130.375 + OxyColor stroke,
130.376 + double strokeThickness = 1.0,
130.377 + LineStyle lineStyle = LineStyle.Solid,
130.378 + OxyPenLineJoin lineJoin = OxyPenLineJoin.Miter,
130.379 + bool aliased = false)
130.380 + {
130.381 + if (rc.SetClip(clippingRectangle))
130.382 + {
130.383 + rc.DrawPolygon(points, fill, stroke, strokeThickness, lineStyle.GetDashArray(), lineJoin, aliased);
130.384 + rc.ResetClip();
130.385 + return;
130.386 + }
130.387 +
130.388 + var clippedPoints = SutherlandHodgmanClipping.ClipPolygon(clippingRectangle, points);
130.389 +
130.390 + rc.DrawPolygon(
130.391 + clippedPoints, fill, stroke, strokeThickness, lineStyle.GetDashArray(), lineJoin, aliased);
130.392 + }
130.393 +
130.394 + /// <summary>
130.395 + /// Draws the clipped rectangle.
130.396 + /// </summary>
130.397 + /// <param name="rc">
130.398 + /// The render context.
130.399 + /// </param>
130.400 + /// <param name="rect">
130.401 + /// The rectangle to draw.
130.402 + /// </param>
130.403 + /// <param name="clippingRectangle">
130.404 + /// The clipping rectangle.
130.405 + /// </param>
130.406 + /// <param name="fill">
130.407 + /// The fill color.
130.408 + /// </param>
130.409 + /// <param name="stroke">
130.410 + /// The stroke color.
130.411 + /// </param>
130.412 + /// <param name="thickness">
130.413 + /// The stroke thickness.
130.414 + /// </param>
130.415 + public static void DrawClippedRectangle(
130.416 + this IRenderContext rc,
130.417 + OxyRect rect,
130.418 + OxyRect clippingRectangle,
130.419 + OxyColor fill,
130.420 + OxyColor stroke,
130.421 + double thickness)
130.422 + {
130.423 + if (rc.SetClip(clippingRectangle))
130.424 + {
130.425 + rc.DrawRectangle(rect, fill, stroke, thickness);
130.426 + rc.ResetClip();
130.427 + return;
130.428 + }
130.429 +
130.430 + var clippedRect = ClipRect(rect, clippingRectangle);
130.431 + if (clippedRect == null)
130.432 + {
130.433 + return;
130.434 + }
130.435 +
130.436 + rc.DrawRectangle(clippedRect.Value, fill, stroke, thickness);
130.437 + }
130.438 +
130.439 + /// <summary>
130.440 + /// Draws the clipped rectangle as a polygon.
130.441 + /// </summary>
130.442 + /// <param name="rc">
130.443 + /// The render context.
130.444 + /// </param>
130.445 + /// <param name="rect">
130.446 + /// The rectangle to draw.
130.447 + /// </param>
130.448 + /// <param name="clippingRectangle">
130.449 + /// The clipping rectangle.
130.450 + /// </param>
130.451 + /// <param name="fill">
130.452 + /// The fill color.
130.453 + /// </param>
130.454 + /// <param name="stroke">
130.455 + /// The stroke color.
130.456 + /// </param>
130.457 + /// <param name="thickness">
130.458 + /// The stroke thickness.
130.459 + /// </param>
130.460 + public static void DrawClippedRectangleAsPolygon(
130.461 + this IRenderContext rc,
130.462 + OxyRect rect,
130.463 + OxyRect clippingRectangle,
130.464 + OxyColor fill,
130.465 + OxyColor stroke,
130.466 + double thickness)
130.467 + {
130.468 + if (rc.SetClip(clippingRectangle))
130.469 + {
130.470 + rc.DrawRectangleAsPolygon(rect, fill, stroke, thickness);
130.471 + rc.ResetClip();
130.472 + return;
130.473 + }
130.474 +
130.475 + var clippedRect = ClipRect(rect, clippingRectangle);
130.476 + if (clippedRect == null)
130.477 + {
130.478 + return;
130.479 + }
130.480 +
130.481 + rc.DrawRectangleAsPolygon(clippedRect.Value, fill, stroke, thickness);
130.482 + }
130.483 +
130.484 + /// <summary>
130.485 + /// Draws a clipped ellipse.
130.486 + /// </summary>
130.487 + /// <param name="rc">The render context.</param>
130.488 + /// <param name="clippingRectangle">The clipping rectangle.</param>
130.489 + /// <param name="rect">The rectangle.</param>
130.490 + /// <param name="fill">The fill color.</param>
130.491 + /// <param name="stroke">The stroke color.</param>
130.492 + /// <param name="thickness">The stroke thickness.</param>
130.493 + /// <param name="n">The number of points around the ellipse.</param>
130.494 + public static void DrawClippedEllipse(
130.495 + this IRenderContext rc,
130.496 + OxyRect clippingRectangle,
130.497 + OxyRect rect,
130.498 + OxyColor fill,
130.499 + OxyColor stroke,
130.500 + double thickness,
130.501 + int n = 100)
130.502 + {
130.503 + if (rc.SetClip(clippingRectangle))
130.504 + {
130.505 + rc.DrawEllipse(rect, fill, stroke, thickness);
130.506 + rc.ResetClip();
130.507 + return;
130.508 + }
130.509 +
130.510 + var points = new ScreenPoint[n];
130.511 + double cx = (rect.Left + rect.Right) / 2;
130.512 + double cy = (rect.Top + rect.Bottom) / 2;
130.513 + double rx = (rect.Right - rect.Left) / 2;
130.514 + double ry = (rect.Bottom - rect.Top) / 2;
130.515 + for (int i = 0; i < n; i++)
130.516 + {
130.517 + double a = Math.PI * 2 * i / (n - 1);
130.518 + points[i] = new ScreenPoint(cx + (rx * Math.Cos(a)), cy + (ry * Math.Sin(a)));
130.519 + }
130.520 +
130.521 + rc.DrawClippedPolygon(points, clippingRectangle, 4, fill, stroke, thickness);
130.522 + }
130.523 +
130.524 + /// <summary>
130.525 + /// Draws the clipped text.
130.526 + /// </summary>
130.527 + /// <param name="rc">The rendering context.</param>
130.528 + /// <param name="clippingRectangle">The clipping rectangle.</param>
130.529 + /// <param name="p">The position.</param>
130.530 + /// <param name="text">The text.</param>
130.531 + /// <param name="fill">The fill color.</param>
130.532 + /// <param name="fontFamily">The font family.</param>
130.533 + /// <param name="fontSize">Size of the font.</param>
130.534 + /// <param name="fontWeight">The font weight.</param>
130.535 + /// <param name="rotate">The rotation angle.</param>
130.536 + /// <param name="horizontalAlignment">The horizontal align.</param>
130.537 + /// <param name="verticalAlignment">The vertical align.</param>
130.538 + /// <param name="maxSize">Size of the max.</param>
130.539 + public static void DrawClippedText(
130.540 + this IRenderContext rc,
130.541 + OxyRect clippingRectangle,
130.542 + ScreenPoint p,
130.543 + string text,
130.544 + OxyColor fill,
130.545 + string fontFamily = null,
130.546 + double fontSize = 10,
130.547 + double fontWeight = 500,
130.548 + double rotate = 0,
130.549 + HorizontalAlignment horizontalAlignment = HorizontalAlignment.Left,
130.550 + VerticalAlignment verticalAlignment = VerticalAlignment.Top,
130.551 + OxySize? maxSize = null)
130.552 + {
130.553 + if (rc.SetClip(clippingRectangle))
130.554 + {
130.555 + rc.DrawText(p, text, fill, fontFamily, fontSize, fontWeight, rotate, horizontalAlignment, verticalAlignment, maxSize);
130.556 + rc.ResetClip();
130.557 + return;
130.558 + }
130.559 +
130.560 + // fall back simply check position
130.561 + if (clippingRectangle.Contains(p.X, p.Y))
130.562 + {
130.563 + rc.DrawText(p, text, fill, fontFamily, fontSize, fontWeight, rotate, horizontalAlignment, verticalAlignment, maxSize);
130.564 + }
130.565 + }
130.566 +
130.567 + /// <summary>
130.568 + /// Draws a line specified by coordinates.
130.569 + /// </summary>
130.570 + /// <param name="rc">
130.571 + /// The render context.
130.572 + /// </param>
130.573 + /// <param name="x0">
130.574 + /// The x0.
130.575 + /// </param>
130.576 + /// <param name="y0">
130.577 + /// The y0.
130.578 + /// </param>
130.579 + /// <param name="x1">
130.580 + /// The x1.
130.581 + /// </param>
130.582 + /// <param name="y1">
130.583 + /// The y1.
130.584 + /// </param>
130.585 + /// <param name="pen">
130.586 + /// The pen.
130.587 + /// </param>
130.588 + /// <param name="aliased">
130.589 + /// Aliased line if set to <c>true</c>.
130.590 + /// </param>
130.591 + public static void DrawLine(
130.592 + this IRenderContext rc, double x0, double y0, double x1, double y1, OxyPen pen, bool aliased = true)
130.593 + {
130.594 + if (pen == null)
130.595 + {
130.596 + return;
130.597 + }
130.598 +
130.599 + rc.DrawLine(
130.600 + new[] { new ScreenPoint(x0, y0), new ScreenPoint(x1, y1) },
130.601 + pen.Color,
130.602 + pen.Thickness,
130.603 + pen.DashArray,
130.604 + pen.LineJoin,
130.605 + aliased);
130.606 + }
130.607 +
130.608 + /// <summary>
130.609 + /// Draws the line segments.
130.610 + /// </summary>
130.611 + /// <param name="rc">
130.612 + /// The render context.
130.613 + /// </param>
130.614 + /// <param name="points">
130.615 + /// The points.
130.616 + /// </param>
130.617 + /// <param name="pen">
130.618 + /// The pen.
130.619 + /// </param>
130.620 + /// <param name="aliased">
130.621 + /// if set to <c>true</c> [aliased].
130.622 + /// </param>
130.623 + public static void DrawLineSegments(
130.624 + this IRenderContext rc, IList<ScreenPoint> points, OxyPen pen, bool aliased = true)
130.625 + {
130.626 + if (pen == null)
130.627 + {
130.628 + return;
130.629 + }
130.630 +
130.631 + rc.DrawLineSegments(points, pen.Color, pen.Thickness, pen.DashArray, pen.LineJoin, aliased);
130.632 + }
130.633 +
130.634 + /// <summary>
130.635 + /// Renders the marker.
130.636 + /// </summary>
130.637 + /// <param name="rc">The render context.</param>
130.638 + /// <param name="p">The center point of the marker.</param>
130.639 + /// <param name="clippingRect">The clipping rectangle.</param>
130.640 + /// <param name="type">The marker type.</param>
130.641 + /// <param name="outline">The outline.</param>
130.642 + /// <param name="size">The size of the marker.</param>
130.643 + /// <param name="fill">The fill color.</param>
130.644 + /// <param name="stroke">The stroke color.</param>
130.645 + /// <param name="strokeThickness">The stroke thickness.</param>
130.646 + public static void DrawMarker(
130.647 + this IRenderContext rc,
130.648 + ScreenPoint p,
130.649 + OxyRect clippingRect,
130.650 + MarkerType type,
130.651 + IList<ScreenPoint> outline,
130.652 + double size,
130.653 + OxyColor fill,
130.654 + OxyColor stroke,
130.655 + double strokeThickness)
130.656 + {
130.657 + rc.DrawMarkers(new[] { p }, clippingRect, type, outline, new[] { size }, fill, stroke, strokeThickness);
130.658 + }
130.659 +
130.660 + /// <summary>
130.661 + /// Draws a list of markers.
130.662 + /// </summary>
130.663 + /// <param name="rc">
130.664 + /// The render context.
130.665 + /// </param>
130.666 + /// <param name="markerPoints">
130.667 + /// The marker points.
130.668 + /// </param>
130.669 + /// <param name="clippingRect">
130.670 + /// The clipping rectangle.
130.671 + /// </param>
130.672 + /// <param name="markerType">
130.673 + /// Type of the marker.
130.674 + /// </param>
130.675 + /// <param name="markerOutline">
130.676 + /// The marker outline.
130.677 + /// </param>
130.678 + /// <param name="markerSize">
130.679 + /// Size of the marker.
130.680 + /// </param>
130.681 + /// <param name="markerFill">
130.682 + /// The marker fill.
130.683 + /// </param>
130.684 + /// <param name="markerStroke">
130.685 + /// The marker stroke.
130.686 + /// </param>
130.687 + /// <param name="markerStrokeThickness">
130.688 + /// The marker stroke thickness.
130.689 + /// </param>
130.690 + /// <param name="resolution">
130.691 + /// The resolution.
130.692 + /// </param>
130.693 + /// <param name="binOffset">
130.694 + /// The bin Offset.
130.695 + /// </param>
130.696 + public static void DrawMarkers(
130.697 + this IRenderContext rc,
130.698 + IList<ScreenPoint> markerPoints,
130.699 + OxyRect clippingRect,
130.700 + MarkerType markerType,
130.701 + IList<ScreenPoint> markerOutline,
130.702 + double markerSize,
130.703 + OxyColor markerFill,
130.704 + OxyColor markerStroke,
130.705 + double markerStrokeThickness,
130.706 + int resolution = 0,
130.707 + ScreenPoint binOffset = new ScreenPoint())
130.708 + {
130.709 + DrawMarkers(
130.710 + rc,
130.711 + markerPoints,
130.712 + clippingRect,
130.713 + markerType,
130.714 + markerOutline,
130.715 + new[] { markerSize },
130.716 + markerFill,
130.717 + markerStroke,
130.718 + markerStrokeThickness,
130.719 + resolution,
130.720 + binOffset);
130.721 + }
130.722 +
130.723 + /// <summary>
130.724 + /// Draws a list of markers.
130.725 + /// </summary>
130.726 + /// <param name="rc">
130.727 + /// The render context.
130.728 + /// </param>
130.729 + /// <param name="markerPoints">
130.730 + /// The marker points.
130.731 + /// </param>
130.732 + /// <param name="clippingRect">
130.733 + /// The clipping rectangle.
130.734 + /// </param>
130.735 + /// <param name="markerType">
130.736 + /// Type of the marker.
130.737 + /// </param>
130.738 + /// <param name="markerOutline">
130.739 + /// The marker outline.
130.740 + /// </param>
130.741 + /// <param name="markerSize">
130.742 + /// Size of the markers.
130.743 + /// </param>
130.744 + /// <param name="markerFill">
130.745 + /// The marker fill.
130.746 + /// </param>
130.747 + /// <param name="markerStroke">
130.748 + /// The marker stroke.
130.749 + /// </param>
130.750 + /// <param name="markerStrokeThickness">
130.751 + /// The marker stroke thickness.
130.752 + /// </param>
130.753 + /// <param name="resolution">
130.754 + /// The resolution.
130.755 + /// </param>
130.756 + /// <param name="binOffset">
130.757 + /// The bin Offset.
130.758 + /// </param>
130.759 + public static void DrawMarkers(
130.760 + this IRenderContext rc,
130.761 + IList<ScreenPoint> markerPoints,
130.762 + OxyRect clippingRect,
130.763 + MarkerType markerType,
130.764 + IList<ScreenPoint> markerOutline,
130.765 + IList<double> markerSize,
130.766 + OxyColor markerFill,
130.767 + OxyColor markerStroke,
130.768 + double markerStrokeThickness,
130.769 + int resolution = 0,
130.770 + ScreenPoint binOffset = new ScreenPoint())
130.771 + {
130.772 + if (markerType == MarkerType.None)
130.773 + {
130.774 + return;
130.775 + }
130.776 +
130.777 + int n = markerPoints.Count;
130.778 + var ellipses = new List<OxyRect>(n);
130.779 + var rects = new List<OxyRect>(n);
130.780 + var polygons = new List<IList<ScreenPoint>>(n);
130.781 + var lines = new List<ScreenPoint>(n);
130.782 +
130.783 + var hashset = new Dictionary<uint, bool>();
130.784 +
130.785 + int i = 0;
130.786 +
130.787 + double minx = clippingRect.Left;
130.788 + double maxx = clippingRect.Right;
130.789 + double miny = clippingRect.Top;
130.790 + double maxy = clippingRect.Bottom;
130.791 +
130.792 + foreach (var p in markerPoints)
130.793 + {
130.794 + if (resolution > 1)
130.795 + {
130.796 + var x = (int)((p.X - binOffset.X) / resolution);
130.797 + var y = (int)((p.Y - binOffset.Y) / resolution);
130.798 + uint hash = (uint)(x << 16) + (uint)y;
130.799 + if (hashset.ContainsKey(hash))
130.800 + {
130.801 + i++;
130.802 + continue;
130.803 + }
130.804 +
130.805 + hashset.Add(hash, true);
130.806 + }
130.807 +
130.808 + bool outside = p.x < minx || p.x > maxx || p.y < miny || p.y > maxy;
130.809 + if (!outside)
130.810 + {
130.811 + int j = i < markerSize.Count ? i : 0;
130.812 + AddMarkerGeometry(p, markerType, markerOutline, markerSize[j], ellipses, rects, polygons, lines);
130.813 + }
130.814 +
130.815 + i++;
130.816 + }
130.817 +
130.818 + if (ellipses.Count > 0)
130.819 + {
130.820 + rc.DrawEllipses(ellipses, markerFill, markerStroke, markerStrokeThickness);
130.821 + }
130.822 +
130.823 + if (rects.Count > 0)
130.824 + {
130.825 + rc.DrawRectangles(rects, markerFill, markerStroke, markerStrokeThickness);
130.826 + }
130.827 +
130.828 + if (polygons.Count > 0)
130.829 + {
130.830 + rc.DrawPolygons(polygons, markerFill, markerStroke, markerStrokeThickness);
130.831 + }
130.832 +
130.833 + if (lines.Count > 0)
130.834 + {
130.835 + rc.DrawLineSegments(lines, markerStroke, markerStrokeThickness);
130.836 + }
130.837 + }
130.838 +
130.839 + /// <summary>
130.840 + /// Draws the rectangle as an aliased polygon.
130.841 + /// (makes sure pixel alignment is the same as for lines)
130.842 + /// </summary>
130.843 + /// <param name="rc">
130.844 + /// The render context.
130.845 + /// </param>
130.846 + /// <param name="rect">
130.847 + /// The rectangle.
130.848 + /// </param>
130.849 + /// <param name="fill">
130.850 + /// The fill.
130.851 + /// </param>
130.852 + /// <param name="stroke">
130.853 + /// The stroke.
130.854 + /// </param>
130.855 + /// <param name="thickness">
130.856 + /// The thickness.
130.857 + /// </param>
130.858 + public static void DrawRectangleAsPolygon(
130.859 + this IRenderContext rc, OxyRect rect, OxyColor fill, OxyColor stroke, double thickness)
130.860 + {
130.861 + var sp0 = new ScreenPoint(rect.Left, rect.Top);
130.862 + var sp1 = new ScreenPoint(rect.Right, rect.Top);
130.863 + var sp2 = new ScreenPoint(rect.Right, rect.Bottom);
130.864 + var sp3 = new ScreenPoint(rect.Left, rect.Bottom);
130.865 + rc.DrawPolygon(new[] { sp0, sp1, sp2, sp3 }, fill, stroke, thickness, null, OxyPenLineJoin.Miter, true);
130.866 + }
130.867 +
130.868 + /// <summary>
130.869 + /// Draws the rectangle as an aliased polygon.
130.870 + /// (makes sure pixel alignment is the same as for lines)
130.871 + /// </summary>
130.872 + /// <param name="rc">
130.873 + /// The render context.
130.874 + /// </param>
130.875 + /// <param name="rect">
130.876 + /// The rectangle.
130.877 + /// </param>
130.878 + /// <param name="fill">
130.879 + /// The fill.
130.880 + /// </param>
130.881 + /// <param name="stroke">
130.882 + /// The stroke.
130.883 + /// </param>
130.884 + /// <param name="thickness">
130.885 + /// The thickness.
130.886 + /// </param>
130.887 + public static void DrawRectangleAsPolygon(
130.888 + this IRenderContext rc, OxyRect rect, OxyColor fill, OxyColor stroke, OxyThickness thickness)
130.889 + {
130.890 + if (thickness.Left.Equals(thickness.Right) && thickness.Left.Equals(thickness.Top)
130.891 + && thickness.Left.Equals(thickness.Bottom))
130.892 + {
130.893 + DrawRectangleAsPolygon(rc, rect, fill, stroke, thickness.Left);
130.894 + return;
130.895 + }
130.896 +
130.897 + var sp0 = new ScreenPoint(rect.Left, rect.Top);
130.898 + var sp1 = new ScreenPoint(rect.Right, rect.Top);
130.899 + var sp2 = new ScreenPoint(rect.Right, rect.Bottom);
130.900 + var sp3 = new ScreenPoint(rect.Left, rect.Bottom);
130.901 + rc.DrawPolygon(new[] { sp0, sp1, sp2, sp3 }, fill, null, 0, null, OxyPenLineJoin.Miter, true);
130.902 + rc.DrawPolygon(new[] { sp0, sp1 }, null, stroke, thickness.Top, null, OxyPenLineJoin.Miter, true);
130.903 + rc.DrawPolygon(new[] { sp1, sp2 }, null, stroke, thickness.Right, null, OxyPenLineJoin.Miter, true);
130.904 + rc.DrawPolygon(new[] { sp2, sp3 }, null, stroke, thickness.Bottom, null, OxyPenLineJoin.Miter, true);
130.905 + rc.DrawPolygon(new[] { sp3, sp0 }, null, stroke, thickness.Left, null, OxyPenLineJoin.Miter, true);
130.906 + }
130.907 +
130.908 + /// <summary>
130.909 + /// Adds a marker geometry.
130.910 + /// </summary>
130.911 + /// <param name="p">
130.912 + /// The position of the marker.
130.913 + /// </param>
130.914 + /// <param name="type">
130.915 + /// The type.
130.916 + /// </param>
130.917 + /// <param name="outline">
130.918 + /// The outline.
130.919 + /// </param>
130.920 + /// <param name="size">
130.921 + /// The size.
130.922 + /// </param>
130.923 + /// <param name="ellipses">
130.924 + /// The ellipse collection.
130.925 + /// </param>
130.926 + /// <param name="rects">
130.927 + /// The rectangle collection.
130.928 + /// </param>
130.929 + /// <param name="polygons">
130.930 + /// The polygon collection.
130.931 + /// </param>
130.932 + /// <param name="lines">
130.933 + /// The line collection.
130.934 + /// </param>
130.935 + private static void AddMarkerGeometry(
130.936 + ScreenPoint p,
130.937 + MarkerType type,
130.938 + IEnumerable<ScreenPoint> outline,
130.939 + double size,
130.940 + IList<OxyRect> ellipses,
130.941 + IList<OxyRect> rects,
130.942 + IList<IList<ScreenPoint>> polygons,
130.943 + IList<ScreenPoint> lines)
130.944 + {
130.945 + if (type == MarkerType.Custom)
130.946 + {
130.947 + if (outline == null)
130.948 + {
130.949 + throw new ArgumentNullException("outline", "The outline should be set when MarkerType is 'Custom'.");
130.950 + }
130.951 +
130.952 + var poly = outline.Select(o => new ScreenPoint(p.X + (o.x * size), p.Y + (o.y * size))).ToList();
130.953 + polygons.Add(poly);
130.954 + return;
130.955 + }
130.956 +
130.957 + switch (type)
130.958 + {
130.959 + case MarkerType.Circle:
130.960 + {
130.961 + ellipses.Add(new OxyRect(p.x - size, p.y - size, size * 2, size * 2));
130.962 + break;
130.963 + }
130.964 +
130.965 + case MarkerType.Square:
130.966 + {
130.967 + rects.Add(new OxyRect(p.x - size, p.y - size, size * 2, size * 2));
130.968 + break;
130.969 + }
130.970 +
130.971 + case MarkerType.Diamond:
130.972 + {
130.973 + polygons.Add(
130.974 + new[]
130.975 + {
130.976 + new ScreenPoint(p.x, p.y - (M2 * size)), new ScreenPoint(p.x + (M2 * size), p.y),
130.977 + new ScreenPoint(p.x, p.y + (M2 * size)), new ScreenPoint(p.x - (M2 * size), p.y)
130.978 + });
130.979 + break;
130.980 + }
130.981 +
130.982 + case MarkerType.Triangle:
130.983 + {
130.984 + polygons.Add(
130.985 + new[]
130.986 + {
130.987 + new ScreenPoint(p.x - size, p.y + (M1 * size)),
130.988 + new ScreenPoint(p.x + size, p.y + (M1 * size)), new ScreenPoint(p.x, p.y - (M2 * size))
130.989 + });
130.990 + break;
130.991 + }
130.992 +
130.993 + case MarkerType.Plus:
130.994 + case MarkerType.Star:
130.995 + {
130.996 + lines.Add(new ScreenPoint(p.x - size, p.y));
130.997 + lines.Add(new ScreenPoint(p.x + size, p.y));
130.998 + lines.Add(new ScreenPoint(p.x, p.y - size));
130.999 + lines.Add(new ScreenPoint(p.x, p.y + size));
130.1000 + break;
130.1001 + }
130.1002 + }
130.1003 +
130.1004 + switch (type)
130.1005 + {
130.1006 + case MarkerType.Cross:
130.1007 + case MarkerType.Star:
130.1008 + {
130.1009 + lines.Add(new ScreenPoint(p.x - (size * M3), p.y - (size * M3)));
130.1010 + lines.Add(new ScreenPoint(p.x + (size * M3), p.y + (size * M3)));
130.1011 + lines.Add(new ScreenPoint(p.x - (size * M3), p.y + (size * M3)));
130.1012 + lines.Add(new ScreenPoint(p.x + (size * M3), p.y - (size * M3)));
130.1013 + break;
130.1014 + }
130.1015 + }
130.1016 + }
130.1017 +
130.1018 + /// <summary>
130.1019 + /// Calculates the clipped version of a rectangle.
130.1020 + /// </summary>
130.1021 + /// <param name="rect">
130.1022 + /// The rectangle to clip.
130.1023 + /// </param>
130.1024 + /// <param name="clippingRectangle">
130.1025 + /// The clipping rectangle.
130.1026 + /// </param>
130.1027 + /// <returns>
130.1028 + /// The clipped rectangle, or null if the rectangle is outside the clipping area.
130.1029 + /// </returns>
130.1030 + private static OxyRect? ClipRect(OxyRect rect, OxyRect clippingRectangle)
130.1031 + {
130.1032 + if (rect.Right < clippingRectangle.Left)
130.1033 + {
130.1034 + return null;
130.1035 + }
130.1036 +
130.1037 + if (rect.Left > clippingRectangle.Right)
130.1038 + {
130.1039 + return null;
130.1040 + }
130.1041 +
130.1042 + if (rect.Top > clippingRectangle.Bottom)
130.1043 + {
130.1044 + return null;
130.1045 + }
130.1046 +
130.1047 + if (rect.Bottom < clippingRectangle.Top)
130.1048 + {
130.1049 + return null;
130.1050 + }
130.1051 +
130.1052 + if (rect.Right > clippingRectangle.Right)
130.1053 + {
130.1054 + rect.Right = clippingRectangle.Right;
130.1055 + }
130.1056 +
130.1057 + if (rect.Left < clippingRectangle.Left)
130.1058 + {
130.1059 + rect.Width = rect.Right - clippingRectangle.Left;
130.1060 + rect.Left = clippingRectangle.Left;
130.1061 + }
130.1062 +
130.1063 + if (rect.Top < clippingRectangle.Top)
130.1064 + {
130.1065 + rect.Height = rect.Bottom - clippingRectangle.Top;
130.1066 + rect.Top = clippingRectangle.Top;
130.1067 + }
130.1068 +
130.1069 + if (rect.Bottom > clippingRectangle.Bottom)
130.1070 + {
130.1071 + rect.Bottom = clippingRectangle.Bottom;
130.1072 + }
130.1073 +
130.1074 + if (rect.Width <= 0 || rect.Height <= 0)
130.1075 + {
130.1076 + return null;
130.1077 + }
130.1078 +
130.1079 + return rect;
130.1080 + }
130.1081 +
130.1082 + /// <summary>
130.1083 + /// Makes sure that a non empty line is visible.
130.1084 + /// </summary>
130.1085 + /// <param name="pts">The points (screen coordinates).</param>
130.1086 + /// <remarks>
130.1087 + /// If the line contains one point, another point is added.
130.1088 + /// If the line contains two points at the same position, the points are moved 2 pixels apart.
130.1089 + /// </remarks>
130.1090 + private static void EnsureNonEmptyLineIsVisible(IList<ScreenPoint> pts)
130.1091 + {
130.1092 + // Check if the line contains two points and they are at the same point
130.1093 + if (pts.Count == 2)
130.1094 + {
130.1095 + if (pts[0].DistanceTo(pts[1]) < 1)
130.1096 + {
130.1097 + // Modify to a small horizontal line to make sure it is being rendered
130.1098 + pts[1] = new ScreenPoint(pts[0].X + 1, pts[0].Y);
130.1099 + pts[0] = new ScreenPoint(pts[0].X - 1, pts[0].Y);
130.1100 + }
130.1101 + }
130.1102 +
130.1103 + // Check if the line contains a single point
130.1104 + if (pts.Count == 1)
130.1105 + {
130.1106 + // Add a second point to make sure the line is being rendered as a small dot
130.1107 + pts.Add(new ScreenPoint(pts[0].X + 1, pts[0].Y));
130.1108 + pts[0] = new ScreenPoint(pts[0].X - 1, pts[0].Y);
130.1109 + }
130.1110 + }
130.1111 + }
130.1112 +}
130.1113 \ No newline at end of file
131.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
131.2 +++ b/External/OxyPlot/OxyPlot/Render/VerticalAxisRenderer.cs Sat Jun 08 16:53:22 2013 +0000
131.3 @@ -0,0 +1,318 @@
131.4 +// --------------------------------------------------------------------------------------------------------------------
131.5 +// <copyright file="VerticalAxisRenderer.cs" company="OxyPlot">
131.6 +// The MIT License (MIT)
131.7 +//
131.8 +// Copyright (c) 2012 Oystein Bjorke
131.9 +//
131.10 +// Permission is hereby granted, free of charge, to any person obtaining a
131.11 +// copy of this software and associated documentation files (the
131.12 +// "Software"), to deal in the Software without restriction, including
131.13 +// without limitation the rights to use, copy, modify, merge, publish,
131.14 +// distribute, sublicense, and/or sell copies of the Software, and to
131.15 +// permit persons to whom the Software is furnished to do so, subject to
131.16 +// the following conditions:
131.17 +//
131.18 +// The above copyright notice and this permission notice shall be included
131.19 +// in all copies or substantial portions of the Software.
131.20 +//
131.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
131.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
131.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
131.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
131.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
131.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
131.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
131.28 +// </copyright>
131.29 +// <summary>
131.30 +// Gets the rotated alignments given the specified angle.
131.31 +// </summary>
131.32 +// --------------------------------------------------------------------------------------------------------------------
131.33 +using System;
131.34 +using System.Diagnostics;
131.35 +
131.36 +namespace OxyPlot
131.37 +{
131.38 + public class VerticalAxisRendererBase : AxisRendererBase
131.39 + {
131.40 + public VerticalAxisRendererBase(IRenderContext rc, PlotModel plot)
131.41 + : base(rc, plot)
131.42 + {
131.43 + }
131.44 +
131.45 + public override void Render(Axis axis)
131.46 + {
131.47 + base.Render(axis);
131.48 +
131.49 + var perpendicularAxis = Plot.DefaultXAxis;
131.50 + bool isHorizontal = true;
131.51 +
131.52 + // Axis position (x or y screen coordinate)
131.53 + double apos = 0;
131.54 +
131.55 + switch (axis.Position)
131.56 + {
131.57 + case AxisPosition.Left:
131.58 + apos = Plot.PlotArea.Left;
131.59 + isHorizontal = false;
131.60 + break;
131.61 + case AxisPosition.Right:
131.62 + apos = Plot.PlotArea.Right;
131.63 + isHorizontal = false;
131.64 + break;
131.65 + case AxisPosition.Top:
131.66 + apos = Plot.PlotArea.Top;
131.67 + perpendicularAxis = Plot.DefaultYAxis;
131.68 + break;
131.69 + case AxisPosition.Bottom:
131.70 + apos = Plot.PlotArea.Bottom;
131.71 + perpendicularAxis = Plot.DefaultYAxis;
131.72 + break;
131.73 + }
131.74 +
131.75 + if (axis.PositionAtZeroCrossing)
131.76 + {
131.77 + apos = perpendicularAxis.Transform(0);
131.78 + }
131.79 +
131.80 + double a0, a1;
131.81 +
131.82 + if (axis.ShowMinorTicks)
131.83 + {
131.84 + GetTickPositions(axis, axis.TickStyle, axis.MinorTickSize, axis.Position, out a0, out a1);
131.85 +
131.86 + foreach (double value in MinorTickValues)
131.87 + {
131.88 + if (value < axis.ActualMinimum || value > axis.ActualMaximum)
131.89 + {
131.90 + continue;
131.91 + }
131.92 +
131.93 + if (MajorTickValues.Contains(value))
131.94 + {
131.95 + continue;
131.96 + }
131.97 +
131.98 + double transformedValue = axis.Transform(value);
131.99 +
131.100 + if (MinorPen != null)
131.101 + {
131.102 + if (isHorizontal)
131.103 + {
131.104 + rc.DrawLine(transformedValue, Plot.PlotArea.Top, transformedValue, Plot.PlotArea.Bottom, MinorPen);
131.105 +
131.106 + }
131.107 + else
131.108 + {
131.109 + rc.DrawLine(Plot.PlotArea.Left, transformedValue, Plot.PlotArea.Right, transformedValue, MinorPen);
131.110 + }
131.111 + }
131.112 + if (isHorizontal)
131.113 + {
131.114 + rc.DrawLine(transformedValue, apos + a0, transformedValue, apos + a1, MinorTickPen);
131.115 +
131.116 + }
131.117 + else
131.118 + {
131.119 + rc.DrawLine(apos + a0, transformedValue, apos + a1, transformedValue, MinorTickPen);
131.120 + }
131.121 + }
131.122 + }
131.123 +
131.124 + GetTickPositions(axis, axis.TickStyle, axis.MajorTickSize, axis.Position, out a0, out a1);
131.125 +
131.126 + double maxWidth = 0;
131.127 + double maxHeight = 0;
131.128 +
131.129 + foreach (double value in MajorTickValues)
131.130 + {
131.131 + if (value < axis.ActualMinimum || value > axis.ActualMaximum)
131.132 + continue;
131.133 +
131.134 + double transformedValue = axis.Transform(value);
131.135 +
131.136 + if (MajorPen != null)
131.137 + {
131.138 + if (isHorizontal)
131.139 + {
131.140 + rc.DrawLine(transformedValue, Plot.PlotArea.Top, transformedValue, Plot.PlotArea.Bottom, MajorPen);
131.141 +
131.142 + }
131.143 + else
131.144 + {
131.145 + rc.DrawLine(Plot.PlotArea.Left, transformedValue, Plot.PlotArea.Right, transformedValue, MajorPen);
131.146 + }
131.147 + }
131.148 +
131.149 + if (isHorizontal)
131.150 + {
131.151 + rc.DrawLine(transformedValue, apos + a0, transformedValue, apos + a1, MajorTickPen);
131.152 +
131.153 + }
131.154 + else
131.155 + {
131.156 + rc.DrawLine(apos + a0, transformedValue, apos + a1, transformedValue, MajorTickPen);
131.157 + }
131.158 +
131.159 + if (value == 0 && axis.PositionAtZeroCrossing)
131.160 + continue;
131.161 +
131.162 + var pt = new ScreenPoint();
131.163 + var ha = HorizontalTextAlign.Right;
131.164 + var va = VerticalTextAlign.Middle;
131.165 + switch (axis.Position)
131.166 + {
131.167 + case AxisPosition.Left:
131.168 + pt = new ScreenPoint(apos + a1 - TICK_DIST, transformedValue);
131.169 + GetRotatedAlignments(axis.Angle, HorizontalTextAlign.Right, VerticalTextAlign.Middle, out ha, out va);
131.170 + break;
131.171 + case AxisPosition.Right:
131.172 + pt = new ScreenPoint(apos + a1 + TICK_DIST, transformedValue);
131.173 + GetRotatedAlignments(axis.Angle, HorizontalTextAlign.Left, VerticalTextAlign.Middle, out ha, out va);
131.174 + break;
131.175 + case AxisPosition.Top:
131.176 + pt = new ScreenPoint(transformedValue, apos + a1 - TICK_DIST);
131.177 + GetRotatedAlignments(axis.Angle, HorizontalTextAlign.Center, VerticalTextAlign.Bottom, out ha, out va);
131.178 + break;
131.179 + case AxisPosition.Bottom:
131.180 + pt = new ScreenPoint(transformedValue, apos + a1 + TICK_DIST);
131.181 + GetRotatedAlignments(axis.Angle, HorizontalTextAlign.Center, VerticalTextAlign.Top, out ha, out va);
131.182 + break;
131.183 +
131.184 + }
131.185 +
131.186 + string text = axis.FormatValue(value);
131.187 + var size = rc.DrawMathText(pt, text, Plot.TextColor,
131.188 + axis.FontFamily, axis.FontSize, axis.FontWeight,
131.189 + axis.Angle, ha, va);
131.190 +
131.191 + maxWidth = Math.Max(maxWidth, size.Width);
131.192 + maxHeight = Math.Max(maxHeight, size.Height);
131.193 + }
131.194 +
131.195 + if (axis.PositionAtZeroCrossing)
131.196 + {
131.197 + double t0 = axis.Transform(0);
131.198 + if (isHorizontal)
131.199 + {
131.200 + rc.DrawLine(t0, Plot.PlotArea.Top, t0, Plot.PlotArea.Bottom, ZeroPen);
131.201 +
131.202 + }
131.203 + else
131.204 + {
131.205 + rc.DrawLine(Plot.PlotArea.Left, t0, Plot.PlotArea.Right, t0, ZeroPen);
131.206 + }
131.207 + }
131.208 +
131.209 + if (axis.ExtraGridlines != null)
131.210 + {
131.211 + foreach (double value in axis.ExtraGridlines)
131.212 + {
131.213 + if (!IsWithin(value, axis.ActualMinimum, axis.ActualMaximum))
131.214 + continue;
131.215 +
131.216 + double transformedValue = axis.Transform(value);
131.217 + if (isHorizontal)
131.218 + {
131.219 + rc.DrawLine(transformedValue, Plot.PlotArea.Top, transformedValue, Plot.PlotArea.Bottom, ExtraPen);
131.220 +
131.221 + }
131.222 + else
131.223 + {
131.224 + rc.DrawLine(Plot.PlotArea.Left, transformedValue, Plot.PlotArea.Right, transformedValue, ExtraPen);
131.225 + }
131.226 + }
131.227 + }
131.228 + if (isHorizontal)
131.229 + {
131.230 + rc.DrawLine(Plot.PlotArea.Left, apos, Plot.PlotArea.Right, apos, MajorPen);
131.231 +
131.232 + }
131.233 + else
131.234 + {
131.235 + rc.DrawLine(apos, Plot.PlotArea.Top, apos, Plot.PlotArea.Bottom, MajorPen);
131.236 + }
131.237 +
131.238 + if (!String.IsNullOrWhiteSpace(axis.Title))
131.239 + {
131.240 + // Axis legend
131.241 + double ymid = axis.Transform((axis.ActualMinimum + axis.ActualMaximum) / 2);
131.242 + double angle = -90;
131.243 + var lpt = new ScreenPoint();
131.244 +
131.245 + var halign = HorizontalTextAlign.Center;
131.246 + var valign = VerticalTextAlign.Top;
131.247 +
131.248 + if (axis.PositionAtZeroCrossing)
131.249 + {
131.250 + ymid = perpendicularAxis.Transform(perpendicularAxis.ActualMaximum);
131.251 + // valign = axis.IsReversed ? VerticalTextAlign.Top : VerticalTextAlign.Bottom;
131.252 + }
131.253 +
131.254 + switch (axis.Position)
131.255 + {
131.256 + case AxisPosition.Left:
131.257 + lpt = new ScreenPoint(AXIS_LEGEND_DIST, ymid);
131.258 + break;
131.259 + case AxisPosition.Right:
131.260 + lpt = new ScreenPoint(rc.Width - AXIS_LEGEND_DIST, ymid);
131.261 + valign = VerticalTextAlign.Bottom;
131.262 + break;
131.263 + case AxisPosition.Top:
131.264 + lpt = new ScreenPoint(ymid, AXIS_LEGEND_DIST);
131.265 + halign = HorizontalTextAlign.Center;
131.266 + valign = VerticalTextAlign.Top;
131.267 + angle = 0;
131.268 + break;
131.269 + case AxisPosition.Bottom:
131.270 + lpt = new ScreenPoint(ymid, rc.Height - AXIS_LEGEND_DIST);
131.271 + halign = HorizontalTextAlign.Center;
131.272 + valign = VerticalTextAlign.Bottom;
131.273 + angle = 0;
131.274 + break;
131.275 + }
131.276 +
131.277 + rc.DrawText(lpt, axis.Title, Plot.TextColor,
131.278 + axis.FontFamily, axis.FontSize, axis.FontWeight,
131.279 + angle, halign, valign);
131.280 + }
131.281 + }
131.282 +
131.283 + /// <summary>
131.284 + /// Gets the rotated alignments given the specified angle.
131.285 + /// </summary>
131.286 + /// <param name="angle">The angle.</param>
131.287 + /// <param name="defaultHorizontalAlignment">The default horizontal alignment.</param>
131.288 + /// <param name="defaultVerticalAlignment">The default vertical alignment.</param>
131.289 + /// <param name="ha">The rotated horizontal alignment.</param>
131.290 + /// <param name="va">The rotated vertical alignment.</param>
131.291 + private static void GetRotatedAlignments(double angle, HorizontalTextAlign defaultHorizontalAlignment, VerticalTextAlign defaultVerticalAlignment,
131.292 + out HorizontalTextAlign ha, out VerticalTextAlign va)
131.293 + {
131.294 + ha = defaultHorizontalAlignment;
131.295 + va = defaultVerticalAlignment;
131.296 +
131.297 + Debug.Assert(angle <= 180 && angle >= -180, "Axis angle should be in the interval [-180,180] degrees.");
131.298 +
131.299 + if (angle > -45 && angle < 45)
131.300 + return;
131.301 + if (angle > 135 || angle < -135)
131.302 + {
131.303 + ha = (HorizontalTextAlign)(-(int)defaultHorizontalAlignment);
131.304 + va = (VerticalTextAlign)(-(int)defaultVerticalAlignment);
131.305 + return;
131.306 + }
131.307 + if (angle > 45)
131.308 + {
131.309 + ha = (HorizontalTextAlign)((int)defaultVerticalAlignment);
131.310 + va = (VerticalTextAlign)(-(int)defaultHorizontalAlignment);
131.311 + return;
131.312 + }
131.313 + if (angle < -45)
131.314 + {
131.315 + ha = (HorizontalTextAlign)(-(int)defaultVerticalAlignment);
131.316 + va = (VerticalTextAlign)((int)defaultHorizontalAlignment);
131.317 + return;
131.318 + }
131.319 + }
131.320 + }
131.321 +}
131.322 \ No newline at end of file
132.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
132.2 +++ b/External/OxyPlot/OxyPlot/Reporting/NamespaceDoc.cs Sat Jun 08 16:53:22 2013 +0000
132.3 @@ -0,0 +1,39 @@
132.4 +// --------------------------------------------------------------------------------------------------------------------
132.5 +// <copyright file="NamespaceDoc.cs" company="OxyPlot">
132.6 +// The MIT License (MIT)
132.7 +//
132.8 +// Copyright (c) 2012 Oystein Bjorke
132.9 +//
132.10 +// Permission is hereby granted, free of charge, to any person obtaining a
132.11 +// copy of this software and associated documentation files (the
132.12 +// "Software"), to deal in the Software without restriction, including
132.13 +// without limitation the rights to use, copy, modify, merge, publish,
132.14 +// distribute, sublicense, and/or sell copies of the Software, and to
132.15 +// permit persons to whom the Software is furnished to do so, subject to
132.16 +// the following conditions:
132.17 +//
132.18 +// The above copyright notice and this permission notice shall be included
132.19 +// in all copies or substantial portions of the Software.
132.20 +//
132.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
132.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
132.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
132.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
132.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
132.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
132.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
132.28 +// </copyright>
132.29 +// --------------------------------------------------------------------------------------------------------------------
132.30 +
132.31 +namespace OxyPlot.Reporting
132.32 +{
132.33 + using System.Runtime.CompilerServices;
132.34 +
132.35 + /// <summary>
132.36 + /// The OxyPlot.Reporting namespace contains a simple report model.
132.37 + /// </summary>
132.38 + [CompilerGenerated]
132.39 + internal class NamespaceDoc
132.40 + {
132.41 + }
132.42 +}
132.43 \ No newline at end of file
133.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
133.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/Content.cs Sat Jun 08 16:53:22 2013 +0000
133.3 @@ -0,0 +1,75 @@
133.4 +// --------------------------------------------------------------------------------------------------------------------
133.5 +// <copyright file="Content.cs" company="OxyPlot">
133.6 +// The MIT License (MIT)
133.7 +//
133.8 +// Copyright (c) 2012 Oystein Bjorke
133.9 +//
133.10 +// Permission is hereby granted, free of charge, to any person obtaining a
133.11 +// copy of this software and associated documentation files (the
133.12 +// "Software"), to deal in the Software without restriction, including
133.13 +// without limitation the rights to use, copy, modify, merge, publish,
133.14 +// distribute, sublicense, and/or sell copies of the Software, and to
133.15 +// permit persons to whom the Software is furnished to do so, subject to
133.16 +// the following conditions:
133.17 +//
133.18 +// The above copyright notice and this permission notice shall be included
133.19 +// in all copies or substantial portions of the Software.
133.20 +//
133.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
133.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
133.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
133.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
133.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
133.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
133.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
133.28 +// </copyright>
133.29 +// --------------------------------------------------------------------------------------------------------------------
133.30 +using System.Collections.Generic;
133.31 +
133.32 +namespace OxyPlot.Reporting
133.33 +{
133.34 + public class Content : Table
133.35 + {
133.36 + public List<ContentItem> Contents { get; set; }
133.37 + public ReportItem Base { get; set; }
133.38 +
133.39 + public Content(ReportItem b)
133.40 + {
133.41 + this.Base = b;
133.42 + Class = "content";
133.43 + Contents = new List<ContentItem>();
133.44 + Columns.Add(new TableColumn(null, "Chapter"));
133.45 + Columns.Add(new TableColumn(null, "Title"));
133.46 + Items = Contents;
133.47 + }
133.48 +
133.49 + public class ContentItem
133.50 + {
133.51 + public string Chapter { get; set; }
133.52 + public string Title { get; set; }
133.53 + }
133.54 +
133.55 + public override void Update()
133.56 + {
133.57 + Contents.Clear();
133.58 + var hh = new HeaderHelper();
133.59 + Search(Base, hh);
133.60 + base.Update();
133.61 + }
133.62 +
133.63 + private void Search(ReportItem item, HeaderHelper hh)
133.64 + {
133.65 + var h = item as Header;
133.66 + if (h != null)
133.67 + {
133.68 + h.Chapter = hh.GetHeader(h.Level);
133.69 + Contents.Add(new ContentItem() { Chapter = h.Chapter, Title = h.Text });
133.70 + }
133.71 + foreach (var c in item.Children)
133.72 + Search(c,hh);
133.73 + }
133.74 + public override void WriteContent(IReportWriter w)
133.75 + {
133.76 + }
133.77 + }
133.78 +}
133.79 \ No newline at end of file
134.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
134.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/Drawing.cs Sat Jun 08 16:53:22 2013 +0000
134.3 @@ -0,0 +1,46 @@
134.4 +// --------------------------------------------------------------------------------------------------------------------
134.5 +// <copyright file="Drawing.cs" company="OxyPlot">
134.6 +// The MIT License (MIT)
134.7 +//
134.8 +// Copyright (c) 2012 Oystein Bjorke
134.9 +//
134.10 +// Permission is hereby granted, free of charge, to any person obtaining a
134.11 +// copy of this software and associated documentation files (the
134.12 +// "Software"), to deal in the Software without restriction, including
134.13 +// without limitation the rights to use, copy, modify, merge, publish,
134.14 +// distribute, sublicense, and/or sell copies of the Software, and to
134.15 +// permit persons to whom the Software is furnished to do so, subject to
134.16 +// the following conditions:
134.17 +//
134.18 +// The above copyright notice and this permission notice shall be included
134.19 +// in all copies or substantial portions of the Software.
134.20 +//
134.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
134.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
134.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
134.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
134.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
134.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
134.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
134.28 +// </copyright>
134.29 +// <summary>
134.30 +// Drawing currently only supports SVG format.
134.31 +// </summary>
134.32 +// --------------------------------------------------------------------------------------------------------------------
134.33 +namespace OxyPlot.Reporting
134.34 +{
134.35 + /// <summary>
134.36 + /// Drawing currently only supports SVG format.
134.37 + /// </summary>
134.38 + public class Drawing : Figure
134.39 + {
134.40 + public enum DrawingFormat { Svg }
134.41 + public DrawingFormat Format { get; set; }
134.42 + public string Content { get; set; }
134.43 +
134.44 + public override void WriteContent(IReportWriter w)
134.45 + {
134.46 + w.WriteDrawing(this);
134.47 + }
134.48 + }
134.49 +}
134.50 \ No newline at end of file
135.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
135.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/DrawingFigure.cs Sat Jun 08 16:53:22 2013 +0000
135.3 @@ -0,0 +1,73 @@
135.4 +// --------------------------------------------------------------------------------------------------------------------
135.5 +// <copyright file="DrawingFigure.cs" company="OxyPlot">
135.6 +// The MIT License (MIT)
135.7 +//
135.8 +// Copyright (c) 2012 Oystein Bjorke
135.9 +//
135.10 +// Permission is hereby granted, free of charge, to any person obtaining a
135.11 +// copy of this software and associated documentation files (the
135.12 +// "Software"), to deal in the Software without restriction, including
135.13 +// without limitation the rights to use, copy, modify, merge, publish,
135.14 +// distribute, sublicense, and/or sell copies of the Software, and to
135.15 +// permit persons to whom the Software is furnished to do so, subject to
135.16 +// the following conditions:
135.17 +//
135.18 +// The above copyright notice and this permission notice shall be included
135.19 +// in all copies or substantial portions of the Software.
135.20 +//
135.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
135.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
135.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
135.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
135.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
135.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
135.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
135.28 +// </copyright>
135.29 +// <summary>
135.30 +// Represents a drawing report item.
135.31 +// </summary>
135.32 +// --------------------------------------------------------------------------------------------------------------------
135.33 +namespace OxyPlot.Reporting
135.34 +{
135.35 + /// <summary>
135.36 + /// Represents a drawing report item.
135.37 + /// </summary>
135.38 + /// <remarks>
135.39 + /// Drawing currently only supports SVG format.
135.40 + /// </remarks>
135.41 + public class DrawingFigure : Figure
135.42 + {
135.43 + /// <summary>
135.44 + /// The drawing format.
135.45 + /// </summary>
135.46 + public enum DrawingFormat
135.47 + {
135.48 + /// <summary>
135.49 + /// The svg.
135.50 + /// </summary>
135.51 + Svg
135.52 + }
135.53 +
135.54 + /// <summary>
135.55 + /// Gets or sets Content.
135.56 + /// </summary>
135.57 + public string Content { get; set; }
135.58 +
135.59 + /// <summary>
135.60 + /// Gets or sets Format.
135.61 + /// </summary>
135.62 + public DrawingFormat Format { get; set; }
135.63 +
135.64 + /// <summary>
135.65 + /// The write content.
135.66 + /// </summary>
135.67 + /// <param name="w">
135.68 + /// The w.
135.69 + /// </param>
135.70 + public override void WriteContent(IReportWriter w)
135.71 + {
135.72 + w.WriteDrawing(this);
135.73 + }
135.74 +
135.75 + }
135.76 +}
135.77 \ No newline at end of file
136.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
136.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/Equation.cs Sat Jun 08 16:53:22 2013 +0000
136.3 @@ -0,0 +1,59 @@
136.4 +// --------------------------------------------------------------------------------------------------------------------
136.5 +// <copyright file="Equation.cs" company="OxyPlot">
136.6 +// The MIT License (MIT)
136.7 +//
136.8 +// Copyright (c) 2012 Oystein Bjorke
136.9 +//
136.10 +// Permission is hereby granted, free of charge, to any person obtaining a
136.11 +// copy of this software and associated documentation files (the
136.12 +// "Software"), to deal in the Software without restriction, including
136.13 +// without limitation the rights to use, copy, modify, merge, publish,
136.14 +// distribute, sublicense, and/or sell copies of the Software, and to
136.15 +// permit persons to whom the Software is furnished to do so, subject to
136.16 +// the following conditions:
136.17 +//
136.18 +// The above copyright notice and this permission notice shall be included
136.19 +// in all copies or substantial portions of the Software.
136.20 +//
136.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
136.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
136.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
136.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
136.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
136.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
136.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
136.28 +// </copyright>
136.29 +// <summary>
136.30 +// Represents an equation.
136.31 +// </summary>
136.32 +// --------------------------------------------------------------------------------------------------------------------
136.33 +namespace OxyPlot.Reporting
136.34 +{
136.35 + /// <summary>
136.36 + /// Represents an equation.
136.37 + /// </summary>
136.38 + public class Equation : ReportItem
136.39 + {
136.40 + /// <summary>
136.41 + /// Gets or sets Caption.
136.42 + /// </summary>
136.43 + public string Caption { get; set; }
136.44 +
136.45 + /// <summary>
136.46 + /// Gets or sets Content.
136.47 + /// </summary>
136.48 + public string Content { get; set; }
136.49 +
136.50 + /// <summary>
136.51 + /// The write content.
136.52 + /// </summary>
136.53 + /// <param name="w">
136.54 + /// The w.
136.55 + /// </param>
136.56 + public override void WriteContent(IReportWriter w)
136.57 + {
136.58 + w.WriteEquation(this);
136.59 + }
136.60 +
136.61 + }
136.62 +}
136.63 \ No newline at end of file
137.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
137.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/Figure.cs Sat Jun 08 16:53:22 2013 +0000
137.3 @@ -0,0 +1,62 @@
137.4 +// --------------------------------------------------------------------------------------------------------------------
137.5 +// <copyright file="Figure.cs" company="OxyPlot">
137.6 +// The MIT License (MIT)
137.7 +//
137.8 +// Copyright (c) 2012 Oystein Bjorke
137.9 +//
137.10 +// Permission is hereby granted, free of charge, to any person obtaining a
137.11 +// copy of this software and associated documentation files (the
137.12 +// "Software"), to deal in the Software without restriction, including
137.13 +// without limitation the rights to use, copy, modify, merge, publish,
137.14 +// distribute, sublicense, and/or sell copies of the Software, and to
137.15 +// permit persons to whom the Software is furnished to do so, subject to
137.16 +// the following conditions:
137.17 +//
137.18 +// The above copyright notice and this permission notice shall be included
137.19 +// in all copies or substantial portions of the Software.
137.20 +//
137.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
137.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
137.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
137.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
137.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
137.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
137.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
137.28 +// </copyright>
137.29 +// <summary>
137.30 +// Represents a figure (abstract base class for DrawingFigure, Image and PlotFigure).
137.31 +// </summary>
137.32 +// --------------------------------------------------------------------------------------------------------------------
137.33 +namespace OxyPlot.Reporting
137.34 +{
137.35 + /// <summary>
137.36 + /// Represents a figure (abstract base class for DrawingFigure, Image and PlotFigure).
137.37 + /// </summary>
137.38 + public abstract class Figure : ReportItem
137.39 + {
137.40 + /// <summary>
137.41 + /// Gets or sets FigureNumber.
137.42 + /// </summary>
137.43 + public int FigureNumber { get; set; }
137.44 +
137.45 + /// <summary>
137.46 + /// Gets or sets FigureText.
137.47 + /// </summary>
137.48 + public string FigureText { get; set; }
137.49 +
137.50 + /// <summary>
137.51 + /// The get full caption.
137.52 + /// </summary>
137.53 + /// <param name="style">
137.54 + /// The style.
137.55 + /// </param>
137.56 + /// <returns>
137.57 + /// The get full caption.
137.58 + /// </returns>
137.59 + public string GetFullCaption(ReportStyle style)
137.60 + {
137.61 + return string.Format(style.FigureTextFormatString, this.FigureNumber, this.FigureText);
137.62 + }
137.63 +
137.64 + }
137.65 +}
137.66 \ No newline at end of file
138.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
138.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/Header.cs Sat Jun 08 16:53:22 2013 +0000
138.3 @@ -0,0 +1,82 @@
138.4 +// --------------------------------------------------------------------------------------------------------------------
138.5 +// <copyright file="Header.cs" company="OxyPlot">
138.6 +// The MIT License (MIT)
138.7 +//
138.8 +// Copyright (c) 2012 Oystein Bjorke
138.9 +//
138.10 +// Permission is hereby granted, free of charge, to any person obtaining a
138.11 +// copy of this software and associated documentation files (the
138.12 +// "Software"), to deal in the Software without restriction, including
138.13 +// without limitation the rights to use, copy, modify, merge, publish,
138.14 +// distribute, sublicense, and/or sell copies of the Software, and to
138.15 +// permit persons to whom the Software is furnished to do so, subject to
138.16 +// the following conditions:
138.17 +//
138.18 +// The above copyright notice and this permission notice shall be included
138.19 +// in all copies or substantial portions of the Software.
138.20 +//
138.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
138.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
138.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
138.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
138.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
138.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
138.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
138.28 +// </copyright>
138.29 +// <summary>
138.30 +// Represents a header.
138.31 +// </summary>
138.32 +// --------------------------------------------------------------------------------------------------------------------
138.33 +namespace OxyPlot.Reporting
138.34 +{
138.35 + /// <summary>
138.36 + /// Represents a header.
138.37 + /// </summary>
138.38 + public class Header : ReportItem
138.39 + {
138.40 + /// <summary>
138.41 + /// Gets or sets the chapter number(s).
138.42 + /// </summary>
138.43 + public string Chapter { get; set; }
138.44 +
138.45 + /// <summary>
138.46 + /// Gets or sets the level of the header (1-5).
138.47 + /// </summary>
138.48 + public int Level { get; set; }
138.49 +
138.50 + /// <summary>
138.51 + /// Gets or sets the header text.
138.52 + /// </summary>
138.53 + public string Text { get; set; }
138.54 +
138.55 + /// <summary>
138.56 + /// The to string.
138.57 + /// </summary>
138.58 + /// <returns>
138.59 + /// The to string.
138.60 + /// </returns>
138.61 + public override string ToString()
138.62 + {
138.63 + string h = string.Empty;
138.64 + if (this.Chapter != null)
138.65 + {
138.66 + h += this.Chapter + " ";
138.67 + }
138.68 +
138.69 + h += this.Text;
138.70 + return h;
138.71 + }
138.72 +
138.73 + /// <summary>
138.74 + /// The write content.
138.75 + /// </summary>
138.76 + /// <param name="w">
138.77 + /// The w.
138.78 + /// </param>
138.79 + public override void WriteContent(IReportWriter w)
138.80 + {
138.81 + w.WriteHeader(this);
138.82 + }
138.83 +
138.84 + }
138.85 +}
138.86 \ No newline at end of file
139.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
139.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/HeaderHelper.cs Sat Jun 08 16:53:22 2013 +0000
139.3 @@ -0,0 +1,82 @@
139.4 +// --------------------------------------------------------------------------------------------------------------------
139.5 +// <copyright file="HeaderHelper.cs" company="OxyPlot">
139.6 +// The MIT License (MIT)
139.7 +//
139.8 +// Copyright (c) 2012 Oystein Bjorke
139.9 +//
139.10 +// Permission is hereby granted, free of charge, to any person obtaining a
139.11 +// copy of this software and associated documentation files (the
139.12 +// "Software"), to deal in the Software without restriction, including
139.13 +// without limitation the rights to use, copy, modify, merge, publish,
139.14 +// distribute, sublicense, and/or sell copies of the Software, and to
139.15 +// permit persons to whom the Software is furnished to do so, subject to
139.16 +// the following conditions:
139.17 +//
139.18 +// The above copyright notice and this permission notice shall be included
139.19 +// in all copies or substantial portions of the Software.
139.20 +//
139.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
139.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
139.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
139.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
139.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
139.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
139.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
139.28 +// </copyright>
139.29 +// <summary>
139.30 +// The header helper.
139.31 +// </summary>
139.32 +// --------------------------------------------------------------------------------------------------------------------
139.33 +namespace OxyPlot.Reporting
139.34 +{
139.35 + /// <summary>
139.36 + /// The header helper.
139.37 + /// </summary>
139.38 + public class HeaderHelper
139.39 + {
139.40 + /// <summary>
139.41 + /// The header level.
139.42 + /// </summary>
139.43 + private readonly int[] headerLevel = new int[10];
139.44 +
139.45 + /// <summary>
139.46 + /// The get header.
139.47 + /// </summary>
139.48 + /// <param name="level">
139.49 + /// The level.
139.50 + /// </param>
139.51 + /// <returns>
139.52 + /// The get header.
139.53 + /// </returns>
139.54 + public string GetHeader(int level)
139.55 + {
139.56 + for (int i = level - 1; i > 0; i--)
139.57 + {
139.58 + if (this.headerLevel[i] == 0)
139.59 + {
139.60 + this.headerLevel[i] = 1;
139.61 + }
139.62 + }
139.63 +
139.64 + this.headerLevel[level]++;
139.65 + for (int i = level + 1; i < 10; i++)
139.66 + {
139.67 + this.headerLevel[i] = 0;
139.68 + }
139.69 +
139.70 + string levelString = string.Empty;
139.71 + for (int i = 1; i <= level; i++)
139.72 + {
139.73 + if (i > 1)
139.74 + {
139.75 + levelString += ".";
139.76 + }
139.77 +
139.78 + levelString += this.headerLevel[i];
139.79 + }
139.80 +
139.81 + return levelString;
139.82 + }
139.83 +
139.84 + }
139.85 +}
139.86 \ No newline at end of file
140.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
140.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/Image.cs Sat Jun 08 16:53:22 2013 +0000
140.3 @@ -0,0 +1,54 @@
140.4 +// --------------------------------------------------------------------------------------------------------------------
140.5 +// <copyright file="Image.cs" company="OxyPlot">
140.6 +// The MIT License (MIT)
140.7 +//
140.8 +// Copyright (c) 2012 Oystein Bjorke
140.9 +//
140.10 +// Permission is hereby granted, free of charge, to any person obtaining a
140.11 +// copy of this software and associated documentation files (the
140.12 +// "Software"), to deal in the Software without restriction, including
140.13 +// without limitation the rights to use, copy, modify, merge, publish,
140.14 +// distribute, sublicense, and/or sell copies of the Software, and to
140.15 +// permit persons to whom the Software is furnished to do so, subject to
140.16 +// the following conditions:
140.17 +//
140.18 +// The above copyright notice and this permission notice shall be included
140.19 +// in all copies or substantial portions of the Software.
140.20 +//
140.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
140.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
140.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
140.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
140.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
140.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
140.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
140.28 +// </copyright>
140.29 +// <summary>
140.30 +// Represents an image report item.
140.31 +// </summary>
140.32 +// --------------------------------------------------------------------------------------------------------------------
140.33 +namespace OxyPlot.Reporting
140.34 +{
140.35 + /// <summary>
140.36 + /// Represents an image report item.
140.37 + /// </summary>
140.38 + public class Image : Figure
140.39 + {
140.40 + /// <summary>
140.41 + /// Gets or sets Source.
140.42 + /// </summary>
140.43 + public string Source { get; set; }
140.44 +
140.45 + /// <summary>
140.46 + /// The write content.
140.47 + /// </summary>
140.48 + /// <param name="w">
140.49 + /// The w.
140.50 + /// </param>
140.51 + public override void WriteContent(IReportWriter w)
140.52 + {
140.53 + w.WriteImage(this);
140.54 + }
140.55 +
140.56 + }
140.57 +}
140.58 \ No newline at end of file
141.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
141.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/ItemsTable.cs Sat Jun 08 16:53:22 2013 +0000
141.3 @@ -0,0 +1,243 @@
141.4 +// --------------------------------------------------------------------------------------------------------------------
141.5 +// <copyright file="ItemsTable.cs" company="OxyPlot">
141.6 +// The MIT License (MIT)
141.7 +//
141.8 +// Copyright (c) 2012 Oystein Bjorke
141.9 +//
141.10 +// Permission is hereby granted, free of charge, to any person obtaining a
141.11 +// copy of this software and associated documentation files (the
141.12 +// "Software"), to deal in the Software without restriction, including
141.13 +// without limitation the rights to use, copy, modify, merge, publish,
141.14 +// distribute, sublicense, and/or sell copies of the Software, and to
141.15 +// permit persons to whom the Software is furnished to do so, subject to
141.16 +// the following conditions:
141.17 +//
141.18 +// The above copyright notice and this permission notice shall be included
141.19 +// in all copies or substantial portions of the Software.
141.20 +//
141.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
141.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
141.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
141.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
141.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
141.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
141.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
141.28 +// </copyright>
141.29 +// <summary>
141.30 +// Represents a table of items.
141.31 +// </summary>
141.32 +// --------------------------------------------------------------------------------------------------------------------
141.33 +namespace OxyPlot.Reporting
141.34 +{
141.35 + using System.Collections;
141.36 + using System.Collections.Generic;
141.37 + using System.Diagnostics;
141.38 + using System.Linq;
141.39 +
141.40 + /// <summary>
141.41 + /// Represents a table of items.
141.42 + /// </summary>
141.43 + public class ItemsTable : Table
141.44 + {
141.45 + /// <summary>
141.46 + /// Initializes a new instance of the <see cref="ItemsTable"/> class.
141.47 + /// </summary>
141.48 + /// <param name="itemsInRows">
141.49 + /// The items in rows.
141.50 + /// </param>
141.51 + public ItemsTable(bool itemsInRows = true)
141.52 + {
141.53 + this.Fields = new List<ItemsTableField>();
141.54 + this.ItemsInRows = itemsInRows;
141.55 + this.Alignment = Alignment.Center;
141.56 + }
141.57 +
141.58 + /// <summary>
141.59 + /// Gets or sets Alignment.
141.60 + /// </summary>
141.61 + public Alignment Alignment { get; set; }
141.62 +
141.63 + /// <summary>
141.64 + /// Gets or sets Fields.
141.65 + /// </summary>
141.66 + public IList<ItemsTableField> Fields { get; set; }
141.67 +
141.68 + /// <summary>
141.69 + /// Gets or sets the items.
141.70 + /// The table will be filled when this property is set.
141.71 + /// </summary>
141.72 + /// <value>The items.</value>
141.73 + public IEnumerable Items { get; set; }
141.74 +
141.75 + /// <summary>
141.76 + /// Gets a value indicating whether ItemsInRows.
141.77 + /// </summary>
141.78 + public bool ItemsInRows { get; private set; }
141.79 +
141.80 + /// <summary>
141.81 + /// The has header.
141.82 + /// </summary>
141.83 + /// <returns>
141.84 + /// The has header.
141.85 + /// </returns>
141.86 + public bool HasHeader()
141.87 + {
141.88 + foreach (var c in this.Fields)
141.89 + {
141.90 + if (c.Header != null)
141.91 + {
141.92 + return true;
141.93 + }
141.94 + }
141.95 +
141.96 + return false;
141.97 + }
141.98 +
141.99 + /// <summary>
141.100 + /// The to array.
141.101 + /// </summary>
141.102 + /// <returns>
141.103 + /// </returns>
141.104 + public string[,] ToArray()
141.105 + {
141.106 + List<object> items = this.Items.Cast<object>().ToList();
141.107 + int nrows = items.Count;
141.108 +
141.109 + bool hasHeader = this.HasHeader();
141.110 + if (hasHeader)
141.111 + {
141.112 + nrows++;
141.113 + }
141.114 +
141.115 + var result = new string[nrows, this.Fields.Count];
141.116 +
141.117 + int row = 0;
141.118 + if (hasHeader)
141.119 + {
141.120 + for (int i = 0; i < this.Fields.Count; i++)
141.121 + {
141.122 + ItemsTableField c = this.Fields[i];
141.123 + result[row, i] = c.Header;
141.124 + }
141.125 +
141.126 + row++;
141.127 + }
141.128 +
141.129 + foreach (var item in items)
141.130 + {
141.131 + for (int i = 0; i < this.Fields.Count; i++)
141.132 + {
141.133 + ItemsTableField c = this.Fields[i];
141.134 + string text = c.GetText(item, this.Report.ActualCulture);
141.135 + result[row, i] = text;
141.136 + }
141.137 +
141.138 + row++;
141.139 + }
141.140 +
141.141 + if (!this.ItemsInRows)
141.142 + {
141.143 + result = Transpose(result);
141.144 + }
141.145 +
141.146 + return result;
141.147 + }
141.148 +
141.149 + /// <summary>
141.150 + /// The update.
141.151 + /// </summary>
141.152 + public override void Update()
141.153 + {
141.154 + base.Update();
141.155 + this.UpdateItems();
141.156 + }
141.157 +
141.158 + /// <summary>
141.159 + /// The update items.
141.160 + /// </summary>
141.161 + public void UpdateItems()
141.162 + {
141.163 + this.Rows.Clear();
141.164 + this.Columns.Clear();
141.165 + if (this.Fields == null || this.Fields.Count == 0)
141.166 + {
141.167 + return;
141.168 + }
141.169 +
141.170 + string[,] cells = this.ToArray();
141.171 +
141.172 + int rows = cells.GetUpperBound(0) + 1;
141.173 + int columns = cells.GetUpperBound(1) + 1;
141.174 + for (int i = 0; i < rows; i++)
141.175 + {
141.176 + var tr = new TableRow();
141.177 + if (this.ItemsInRows)
141.178 + {
141.179 + tr.IsHeader = i == 0;
141.180 + }
141.181 +
141.182 + this.Rows.Add(tr);
141.183 + for (int j = 0; j < columns; j++)
141.184 + {
141.185 + var tc = new TableCell();
141.186 + tc.Content = cells[i, j];
141.187 + tr.Cells.Add(tc);
141.188 + }
141.189 + }
141.190 +
141.191 + for (int j = 0; j < columns; j++)
141.192 + {
141.193 + var tc = new TableColumn();
141.194 + if (this.ItemsInRows)
141.195 + {
141.196 + ItemsTableField f = this.Fields[j];
141.197 + tc.Alignment = f.Alignment;
141.198 + tc.Width = f.Width;
141.199 + }
141.200 + else
141.201 + {
141.202 + tc.IsHeader = j == 0;
141.203 + tc.Alignment = this.Alignment;
141.204 + }
141.205 +
141.206 + this.Columns.Add(tc);
141.207 + }
141.208 + }
141.209 +
141.210 + /// <summary>
141.211 + /// Writes the content of the item.
141.212 + /// </summary>
141.213 + /// <param name="w">
141.214 + /// The writer.
141.215 + /// </param>
141.216 + public override void WriteContent(IReportWriter w)
141.217 + {
141.218 + w.WriteTable(this);
141.219 + }
141.220 +
141.221 + /// <summary>
141.222 + /// The transpose.
141.223 + /// </summary>
141.224 + /// <param name="input">
141.225 + /// The input.
141.226 + /// </param>
141.227 + /// <returns>
141.228 + /// </returns>
141.229 + private static string[,] Transpose(string[,] input)
141.230 + {
141.231 + int rows = input.GetUpperBound(0) + 1;
141.232 + int cols = input.GetUpperBound(1) + 1;
141.233 + var result = new string[cols, rows];
141.234 + for (int i = 0; i < rows; i++)
141.235 + {
141.236 + for (int j = 0; j < cols; j++)
141.237 + {
141.238 + result[j, i] = input[i, j];
141.239 + }
141.240 + }
141.241 +
141.242 + return result;
141.243 + }
141.244 +
141.245 + }
141.246 +}
141.247 \ No newline at end of file
142.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
142.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/ItemsTableField.cs Sat Jun 08 16:53:22 2013 +0000
142.3 @@ -0,0 +1,136 @@
142.4 +// --------------------------------------------------------------------------------------------------------------------
142.5 +// <copyright file="ItemsTableField.cs" company="OxyPlot">
142.6 +// The MIT License (MIT)
142.7 +//
142.8 +// Copyright (c) 2012 Oystein Bjorke
142.9 +//
142.10 +// Permission is hereby granted, free of charge, to any person obtaining a
142.11 +// copy of this software and associated documentation files (the
142.12 +// "Software"), to deal in the Software without restriction, including
142.13 +// without limitation the rights to use, copy, modify, merge, publish,
142.14 +// distribute, sublicense, and/or sell copies of the Software, and to
142.15 +// permit persons to whom the Software is furnished to do so, subject to
142.16 +// the following conditions:
142.17 +//
142.18 +// The above copyright notice and this permission notice shall be included
142.19 +// in all copies or substantial portions of the Software.
142.20 +//
142.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
142.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
142.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
142.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
142.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
142.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
142.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
142.28 +// </copyright>
142.29 +// <summary>
142.30 +// The alignment.
142.31 +// </summary>
142.32 +// --------------------------------------------------------------------------------------------------------------------
142.33 +namespace OxyPlot.Reporting
142.34 +{
142.35 + using System;
142.36 + using System.Reflection;
142.37 +
142.38 + /// <summary>
142.39 + /// The alignment.
142.40 + /// </summary>
142.41 + public enum Alignment
142.42 + {
142.43 + /// <summary>
142.44 + /// The left.
142.45 + /// </summary>
142.46 + Left,
142.47 +
142.48 + /// <summary>
142.49 + /// The right.
142.50 + /// </summary>
142.51 + Right,
142.52 +
142.53 + /// <summary>
142.54 + /// The center.
142.55 + /// </summary>
142.56 + Center
142.57 + }
142.58 +
142.59 + /// <summary>
142.60 + /// Represents a field in an items table.
142.61 + /// </summary>
142.62 + public class ItemsTableField
142.63 + {
142.64 + /// <summary>
142.65 + /// Initializes a new instance of the <see cref="ItemsTableField"/> class.
142.66 + /// </summary>
142.67 + /// <param name="header">
142.68 + /// The header.
142.69 + /// </param>
142.70 + /// <param name="path">
142.71 + /// The path.
142.72 + /// </param>
142.73 + /// <param name="stringFormat">
142.74 + /// The string format.
142.75 + /// </param>
142.76 + /// <param name="alignment">
142.77 + /// The alignment.
142.78 + /// </param>
142.79 + public ItemsTableField(
142.80 + string header, string path, string stringFormat = null, Alignment alignment = Alignment.Center)
142.81 + {
142.82 + this.Header = header;
142.83 + this.Path = path;
142.84 + this.StringFormat = stringFormat;
142.85 + this.Alignment = alignment;
142.86 + }
142.87 +
142.88 + /// <summary>
142.89 + /// Gets or sets Alignment.
142.90 + /// </summary>
142.91 + public Alignment Alignment { get; set; }
142.92 +
142.93 + /// <summary>
142.94 + /// Gets or sets Header.
142.95 + /// </summary>
142.96 + public string Header { get; set; }
142.97 +
142.98 + /// <summary>
142.99 + /// Gets or sets Path.
142.100 + /// </summary>
142.101 + public string Path { get; set; }
142.102 +
142.103 + /// <summary>
142.104 + /// Gets or sets StringFormat.
142.105 + /// </summary>
142.106 + public string StringFormat { get; set; }
142.107 +
142.108 + /// <summary>
142.109 + /// Gets or sets Width.
142.110 + /// </summary>
142.111 + public double Width { get; set; }
142.112 +
142.113 + /// <summary>
142.114 + /// Gets the text.
142.115 + /// </summary>
142.116 + /// <param name="item">
142.117 + /// The item.
142.118 + /// </param>
142.119 + /// <param name="formatProvider">
142.120 + /// The format provider.
142.121 + /// </param>
142.122 + /// <returns>
142.123 + /// The text.
142.124 + /// </returns>
142.125 + public string GetText(object item, IFormatProvider formatProvider)
142.126 + {
142.127 + PropertyInfo pi = item.GetType().GetProperty(this.Path);
142.128 + object o = pi.GetValue(item, null);
142.129 + var of = o as IFormattable;
142.130 + if (of != null)
142.131 + {
142.132 + return of.ToString(this.StringFormat, formatProvider);
142.133 + }
142.134 +
142.135 + return o != null ? o.ToString() : null;
142.136 + }
142.137 +
142.138 + }
142.139 +}
142.140 \ No newline at end of file
143.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
143.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/Paragraph.cs Sat Jun 08 16:53:22 2013 +0000
143.3 @@ -0,0 +1,54 @@
143.4 +// --------------------------------------------------------------------------------------------------------------------
143.5 +// <copyright file="Paragraph.cs" company="OxyPlot">
143.6 +// The MIT License (MIT)
143.7 +//
143.8 +// Copyright (c) 2012 Oystein Bjorke
143.9 +//
143.10 +// Permission is hereby granted, free of charge, to any person obtaining a
143.11 +// copy of this software and associated documentation files (the
143.12 +// "Software"), to deal in the Software without restriction, including
143.13 +// without limitation the rights to use, copy, modify, merge, publish,
143.14 +// distribute, sublicense, and/or sell copies of the Software, and to
143.15 +// permit persons to whom the Software is furnished to do so, subject to
143.16 +// the following conditions:
143.17 +//
143.18 +// The above copyright notice and this permission notice shall be included
143.19 +// in all copies or substantial portions of the Software.
143.20 +//
143.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
143.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
143.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
143.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
143.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
143.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
143.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
143.28 +// </copyright>
143.29 +// <summary>
143.30 +// Represents a paragraph.
143.31 +// </summary>
143.32 +// --------------------------------------------------------------------------------------------------------------------
143.33 +namespace OxyPlot.Reporting
143.34 +{
143.35 + /// <summary>
143.36 + /// Represents a paragraph.
143.37 + /// </summary>
143.38 + public class Paragraph : ReportItem
143.39 + {
143.40 + /// <summary>
143.41 + /// Gets or sets Text.
143.42 + /// </summary>
143.43 + public string Text { get; set; }
143.44 +
143.45 + /// <summary>
143.46 + /// The write content.
143.47 + /// </summary>
143.48 + /// <param name="w">
143.49 + /// The w.
143.50 + /// </param>
143.51 + public override void WriteContent(IReportWriter w)
143.52 + {
143.53 + w.WriteParagraph(this);
143.54 + }
143.55 +
143.56 + }
143.57 +}
143.58 \ No newline at end of file
144.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
144.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/ParagraphStyle.cs Sat Jun 08 16:53:22 2013 +0000
144.3 @@ -0,0 +1,397 @@
144.4 +// --------------------------------------------------------------------------------------------------------------------
144.5 +// <copyright file="ParagraphStyle.cs" company="OxyPlot">
144.6 +// The MIT License (MIT)
144.7 +//
144.8 +// Copyright (c) 2012 Oystein Bjorke
144.9 +//
144.10 +// Permission is hereby granted, free of charge, to any person obtaining a
144.11 +// copy of this software and associated documentation files (the
144.12 +// "Software"), to deal in the Software without restriction, including
144.13 +// without limitation the rights to use, copy, modify, merge, publish,
144.14 +// distribute, sublicense, and/or sell copies of the Software, and to
144.15 +// permit persons to whom the Software is furnished to do so, subject to
144.16 +// the following conditions:
144.17 +//
144.18 +// The above copyright notice and this permission notice shall be included
144.19 +// in all copies or substantial portions of the Software.
144.20 +//
144.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
144.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
144.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
144.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
144.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
144.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
144.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
144.28 +// </copyright>
144.29 +// <summary>
144.30 +// The paragraph style.
144.31 +// </summary>
144.32 +// --------------------------------------------------------------------------------------------------------------------
144.33 +namespace OxyPlot.Reporting
144.34 +{
144.35 + /// <summary>
144.36 + /// The paragraph style.
144.37 + /// </summary>
144.38 + public class ParagraphStyle
144.39 + {
144.40 + /// <summary>
144.41 + /// The default font.
144.42 + /// </summary>
144.43 + private const string DefaultFont = "Arial";
144.44 +
144.45 + /// <summary>
144.46 + /// The default font size.
144.47 + /// </summary>
144.48 + private const double DefaultFontSize = 11;
144.49 +
144.50 + /// <summary>
144.51 + /// The bold.
144.52 + /// </summary>
144.53 + private bool? bold;
144.54 +
144.55 + /// <summary>
144.56 + /// The font family.
144.57 + /// </summary>
144.58 + private string fontFamily;
144.59 +
144.60 + /// <summary>
144.61 + /// The font size.
144.62 + /// </summary>
144.63 + private double? fontSize;
144.64 +
144.65 + /// <summary>
144.66 + /// The italic.
144.67 + /// </summary>
144.68 + private bool? italic;
144.69 +
144.70 + /// <summary>
144.71 + /// The left indentation.
144.72 + /// </summary>
144.73 + private double? leftIndentation;
144.74 +
144.75 + /// <summary>
144.76 + /// The line spacing.
144.77 + /// </summary>
144.78 + private double? lineSpacing;
144.79 +
144.80 + /// <summary>
144.81 + /// The page break before.
144.82 + /// </summary>
144.83 + private bool? pageBreakBefore;
144.84 +
144.85 + /// <summary>
144.86 + /// The right indentation.
144.87 + /// </summary>
144.88 + private double? rightIndentation;
144.89 +
144.90 + /// <summary>
144.91 + /// The spacing after.
144.92 + /// </summary>
144.93 + private double? spacingAfter;
144.94 +
144.95 + /// <summary>
144.96 + /// The spacing before.
144.97 + /// </summary>
144.98 + private double? spacingBefore;
144.99 +
144.100 + /// <summary>
144.101 + /// The text color.
144.102 + /// </summary>
144.103 + private OxyColor textColor;
144.104 +
144.105 + /// <summary>
144.106 + /// Gets or sets BasedOn.
144.107 + /// </summary>
144.108 + public ParagraphStyle BasedOn { get; set; }
144.109 +
144.110 + /// <summary>
144.111 + /// Gets or sets a value indicating whether Bold.
144.112 + /// </summary>
144.113 + public bool Bold
144.114 + {
144.115 + get
144.116 + {
144.117 + if (this.bold != null)
144.118 + {
144.119 + return this.bold.Value;
144.120 + }
144.121 +
144.122 + if (this.BasedOn != null)
144.123 + {
144.124 + return this.BasedOn.Bold;
144.125 + }
144.126 +
144.127 + return false;
144.128 + }
144.129 +
144.130 + set
144.131 + {
144.132 + this.bold = value;
144.133 + }
144.134 + }
144.135 +
144.136 + /// <summary>
144.137 + /// Gets or sets FontFamily.
144.138 + /// </summary>
144.139 + public string FontFamily
144.140 + {
144.141 + get
144.142 + {
144.143 + if (this.fontFamily != null)
144.144 + {
144.145 + return this.fontFamily;
144.146 + }
144.147 +
144.148 + if (this.BasedOn != null)
144.149 + {
144.150 + return this.BasedOn.FontFamily;
144.151 + }
144.152 +
144.153 + return DefaultFont;
144.154 + }
144.155 +
144.156 + set
144.157 + {
144.158 + this.fontFamily = value;
144.159 + }
144.160 + }
144.161 +
144.162 + /// <summary>
144.163 + /// Gets or sets FontSize.
144.164 + /// </summary>
144.165 + public double FontSize
144.166 + {
144.167 + get
144.168 + {
144.169 + if (this.fontSize != null)
144.170 + {
144.171 + return this.fontSize.Value;
144.172 + }
144.173 +
144.174 + if (this.BasedOn != null)
144.175 + {
144.176 + return this.BasedOn.FontSize;
144.177 + }
144.178 +
144.179 + return DefaultFontSize;
144.180 + }
144.181 +
144.182 + set
144.183 + {
144.184 + this.fontSize = value;
144.185 + }
144.186 + }
144.187 +
144.188 + /// <summary>
144.189 + /// Gets or sets a value indicating whether Italic.
144.190 + /// </summary>
144.191 + public bool Italic
144.192 + {
144.193 + get
144.194 + {
144.195 + if (this.italic != null)
144.196 + {
144.197 + return this.italic.Value;
144.198 + }
144.199 +
144.200 + if (this.BasedOn != null)
144.201 + {
144.202 + return this.BasedOn.Italic;
144.203 + }
144.204 +
144.205 + return false;
144.206 + }
144.207 +
144.208 + set
144.209 + {
144.210 + this.italic = value;
144.211 + }
144.212 + }
144.213 +
144.214 + /// <summary>
144.215 + /// Gets or sets LeftIndentation.
144.216 + /// </summary>
144.217 + public double LeftIndentation
144.218 + {
144.219 + get
144.220 + {
144.221 + if (this.leftIndentation != null)
144.222 + {
144.223 + return this.leftIndentation.Value;
144.224 + }
144.225 +
144.226 + if (this.BasedOn != null)
144.227 + {
144.228 + return this.BasedOn.LeftIndentation;
144.229 + }
144.230 +
144.231 + return 0;
144.232 + }
144.233 +
144.234 + set
144.235 + {
144.236 + this.leftIndentation = value;
144.237 + }
144.238 + }
144.239 +
144.240 + /// <summary>
144.241 + /// Gets or sets LineSpacing.
144.242 + /// </summary>
144.243 + public double LineSpacing
144.244 + {
144.245 + get
144.246 + {
144.247 + if (this.lineSpacing != null)
144.248 + {
144.249 + return this.lineSpacing.Value;
144.250 + }
144.251 +
144.252 + if (this.BasedOn != null)
144.253 + {
144.254 + return this.BasedOn.LineSpacing;
144.255 + }
144.256 +
144.257 + return 1;
144.258 + }
144.259 +
144.260 + set
144.261 + {
144.262 + this.lineSpacing = value;
144.263 + }
144.264 + }
144.265 +
144.266 + /// <summary>
144.267 + /// Gets or sets a value indicating whether PageBreakBefore.
144.268 + /// </summary>
144.269 + public bool PageBreakBefore
144.270 + {
144.271 + get
144.272 + {
144.273 + if (this.pageBreakBefore != null)
144.274 + {
144.275 + return this.pageBreakBefore.Value;
144.276 + }
144.277 +
144.278 + if (this.BasedOn != null)
144.279 + {
144.280 + return this.BasedOn.PageBreakBefore;
144.281 + }
144.282 +
144.283 + return false;
144.284 + }
144.285 +
144.286 + set
144.287 + {
144.288 + this.pageBreakBefore = value;
144.289 + }
144.290 + }
144.291 +
144.292 + /// <summary>
144.293 + /// Gets or sets RightIndentation.
144.294 + /// </summary>
144.295 + public double RightIndentation
144.296 + {
144.297 + get
144.298 + {
144.299 + if (this.rightIndentation != null)
144.300 + {
144.301 + return this.rightIndentation.Value;
144.302 + }
144.303 +
144.304 + if (this.BasedOn != null)
144.305 + {
144.306 + return this.BasedOn.RightIndentation;
144.307 + }
144.308 +
144.309 + return 0;
144.310 + }
144.311 +
144.312 + set
144.313 + {
144.314 + this.rightIndentation = value;
144.315 + }
144.316 + }
144.317 +
144.318 + /// <summary>
144.319 + /// Gets or sets SpacingAfter.
144.320 + /// </summary>
144.321 + public double SpacingAfter
144.322 + {
144.323 + get
144.324 + {
144.325 + if (this.spacingAfter != null)
144.326 + {
144.327 + return this.spacingAfter.Value;
144.328 + }
144.329 +
144.330 + if (this.BasedOn != null)
144.331 + {
144.332 + return this.BasedOn.SpacingAfter;
144.333 + }
144.334 +
144.335 + return 0;
144.336 + }
144.337 +
144.338 + set
144.339 + {
144.340 + this.spacingAfter = value;
144.341 + }
144.342 + }
144.343 +
144.344 + /// <summary>
144.345 + /// Gets or sets SpacingBefore.
144.346 + /// </summary>
144.347 + public double SpacingBefore
144.348 + {
144.349 + get
144.350 + {
144.351 + if (this.spacingBefore != null)
144.352 + {
144.353 + return this.spacingBefore.Value;
144.354 + }
144.355 +
144.356 + if (this.BasedOn != null)
144.357 + {
144.358 + return this.BasedOn.SpacingBefore;
144.359 + }
144.360 +
144.361 + return 0;
144.362 + }
144.363 +
144.364 + set
144.365 + {
144.366 + this.spacingBefore = value;
144.367 + }
144.368 + }
144.369 +
144.370 + /// <summary>
144.371 + /// Gets or sets TextColor.
144.372 + /// </summary>
144.373 + public OxyColor TextColor
144.374 + {
144.375 + get
144.376 + {
144.377 + if (this.textColor != null)
144.378 + {
144.379 + return this.textColor;
144.380 + }
144.381 +
144.382 + if (this.BasedOn != null)
144.383 + {
144.384 + return this.BasedOn.TextColor;
144.385 + }
144.386 +
144.387 + return OxyColors.Black;
144.388 + }
144.389 +
144.390 + set
144.391 + {
144.392 + this.textColor = value;
144.393 + }
144.394 + }
144.395 +
144.396 + // margin
144.397 + // padding
144.398 + // borders
144.399 + }
144.400 +}
144.401 \ No newline at end of file
145.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
145.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/Plot.cs Sat Jun 08 16:53:22 2013 +0000
145.3 @@ -0,0 +1,40 @@
145.4 +// --------------------------------------------------------------------------------------------------------------------
145.5 +// <copyright file="Plot.cs" company="OxyPlot">
145.6 +// The MIT License (MIT)
145.7 +//
145.8 +// Copyright (c) 2012 Oystein Bjorke
145.9 +//
145.10 +// Permission is hereby granted, free of charge, to any person obtaining a
145.11 +// copy of this software and associated documentation files (the
145.12 +// "Software"), to deal in the Software without restriction, including
145.13 +// without limitation the rights to use, copy, modify, merge, publish,
145.14 +// distribute, sublicense, and/or sell copies of the Software, and to
145.15 +// permit persons to whom the Software is furnished to do so, subject to
145.16 +// the following conditions:
145.17 +//
145.18 +// The above copyright notice and this permission notice shall be included
145.19 +// in all copies or substantial portions of the Software.
145.20 +//
145.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
145.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
145.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
145.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
145.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
145.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
145.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
145.28 +// </copyright>
145.29 +// --------------------------------------------------------------------------------------------------------------------
145.30 +namespace OxyPlot.Reporting
145.31 +{
145.32 + public class Plot : Figure
145.33 + {
145.34 + public PlotModel PlotModel { get; set; }
145.35 + public double Width { get; set; }
145.36 + public double Height { get; set; }
145.37 +
145.38 + public override void WriteContent(IReportWriter w)
145.39 + {
145.40 + w.WritePlot(this);
145.41 + }
145.42 + }
145.43 +}
145.44 \ No newline at end of file
146.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
146.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/PlotFigure.cs Sat Jun 08 16:53:22 2013 +0000
146.3 @@ -0,0 +1,64 @@
146.4 +// --------------------------------------------------------------------------------------------------------------------
146.5 +// <copyright file="PlotFigure.cs" company="OxyPlot">
146.6 +// The MIT License (MIT)
146.7 +//
146.8 +// Copyright (c) 2012 Oystein Bjorke
146.9 +//
146.10 +// Permission is hereby granted, free of charge, to any person obtaining a
146.11 +// copy of this software and associated documentation files (the
146.12 +// "Software"), to deal in the Software without restriction, including
146.13 +// without limitation the rights to use, copy, modify, merge, publish,
146.14 +// distribute, sublicense, and/or sell copies of the Software, and to
146.15 +// permit persons to whom the Software is furnished to do so, subject to
146.16 +// the following conditions:
146.17 +//
146.18 +// The above copyright notice and this permission notice shall be included
146.19 +// in all copies or substantial portions of the Software.
146.20 +//
146.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
146.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
146.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
146.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
146.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
146.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
146.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
146.28 +// </copyright>
146.29 +// <summary>
146.30 +// Represents a plot figure.
146.31 +// </summary>
146.32 +// --------------------------------------------------------------------------------------------------------------------
146.33 +namespace OxyPlot.Reporting
146.34 +{
146.35 + /// <summary>
146.36 + /// Represents a plot figure.
146.37 + /// </summary>
146.38 + public class PlotFigure : Figure
146.39 + {
146.40 + /// <summary>
146.41 + /// Gets or sets Height.
146.42 + /// </summary>
146.43 + public double Height { get; set; }
146.44 +
146.45 + /// <summary>
146.46 + /// Gets or sets PlotModel.
146.47 + /// </summary>
146.48 + public PlotModel PlotModel { get; set; }
146.49 +
146.50 + /// <summary>
146.51 + /// Gets or sets Width.
146.52 + /// </summary>
146.53 + public double Width { get; set; }
146.54 +
146.55 + /// <summary>
146.56 + /// The write content.
146.57 + /// </summary>
146.58 + /// <param name="w">
146.59 + /// The w.
146.60 + /// </param>
146.61 + public override void WriteContent(IReportWriter w)
146.62 + {
146.63 + w.WritePlot(this);
146.64 + }
146.65 +
146.66 + }
146.67 +}
146.68 \ No newline at end of file
147.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
147.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/PropertyTable.cs Sat Jun 08 16:53:22 2013 +0000
147.3 @@ -0,0 +1,114 @@
147.4 +// --------------------------------------------------------------------------------------------------------------------
147.5 +// <copyright file="PropertyTable.cs" company="OxyPlot">
147.6 +// The MIT License (MIT)
147.7 +//
147.8 +// Copyright (c) 2012 Oystein Bjorke
147.9 +//
147.10 +// Permission is hereby granted, free of charge, to any person obtaining a
147.11 +// copy of this software and associated documentation files (the
147.12 +// "Software"), to deal in the Software without restriction, including
147.13 +// without limitation the rights to use, copy, modify, merge, publish,
147.14 +// distribute, sublicense, and/or sell copies of the Software, and to
147.15 +// permit persons to whom the Software is furnished to do so, subject to
147.16 +// the following conditions:
147.17 +//
147.18 +// The above copyright notice and this permission notice shall be included
147.19 +// in all copies or substantial portions of the Software.
147.20 +//
147.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
147.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
147.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
147.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
147.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
147.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
147.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
147.28 +// </copyright>
147.29 +// <summary>
147.30 +// Represents a table of autogenerated property values.
147.31 +// </summary>
147.32 +// --------------------------------------------------------------------------------------------------------------------
147.33 +namespace OxyPlot.Reporting
147.34 +{
147.35 + using System;
147.36 + using System.Collections;
147.37 + using System.ComponentModel;
147.38 +
147.39 + /// <summary>
147.40 + /// Represents a table of autogenerated property values.
147.41 + /// </summary>
147.42 + /// <remarks>
147.43 + /// The PropertyTable autogenerates columns or rows based on reflecting the Items type.
147.44 + /// Only [Browsable] properties are included.
147.45 + /// </remarks>
147.46 + public class PropertyTable : ItemsTable
147.47 + {
147.48 + /// <summary>
147.49 + /// Initializes a new instance of the <see cref="PropertyTable"/> class.
147.50 + /// </summary>
147.51 + /// <param name="items">
147.52 + /// The items.
147.53 + /// </param>
147.54 + /// <param name="itemsInRows">
147.55 + /// The items in rows.
147.56 + /// </param>
147.57 + public PropertyTable(IEnumerable items, bool itemsInRows)
147.58 + : base(itemsInRows)
147.59 + {
147.60 + this.Alignment = Alignment.Left;
147.61 + this.UpdateFields(items);
147.62 + this.Items = items;
147.63 + }
147.64 +
147.65 + /// <summary>
147.66 + /// The get item type.
147.67 + /// </summary>
147.68 + /// <param name="items">
147.69 + /// The items.
147.70 + /// </param>
147.71 + /// <returns>
147.72 + /// </returns>
147.73 + private Type GetItemType(IEnumerable items)
147.74 + {
147.75 + Type result = null;
147.76 + foreach (var item in items)
147.77 + {
147.78 + Type t = item.GetType();
147.79 + if (result == null)
147.80 + {
147.81 + result = t;
147.82 + }
147.83 +
147.84 + if (t != result)
147.85 + {
147.86 + return null;
147.87 + }
147.88 + }
147.89 +
147.90 + return result;
147.91 + }
147.92 +
147.93 + /// <summary>
147.94 + /// Updates the fields.
147.95 + /// </summary>
147.96 + /// <param name="items">
147.97 + /// The items.
147.98 + /// </param>
147.99 + private void UpdateFields(IEnumerable items)
147.100 + {
147.101 + Type type = this.GetItemType(items);
147.102 + if (type == null)
147.103 + {
147.104 + return;
147.105 + }
147.106 +
147.107 + this.Columns.Clear();
147.108 +
147.109 + foreach (var pi in type.GetProperties())
147.110 + {
147.111 + // TODO: support Browsable and Displayname attributes
147.112 + var header = pi.Name;
147.113 + this.Fields.Add(new ItemsTableField(header, pi.Name, null, Alignment.Left));
147.114 + }
147.115 + }
147.116 + }
147.117 +}
147.118 \ No newline at end of file
148.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
148.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/Report.cs Sat Jun 08 16:53:22 2013 +0000
148.3 @@ -0,0 +1,87 @@
148.4 +// --------------------------------------------------------------------------------------------------------------------
148.5 +// <copyright file="Report.cs" company="OxyPlot">
148.6 +// The MIT License (MIT)
148.7 +//
148.8 +// Copyright (c) 2012 Oystein Bjorke
148.9 +//
148.10 +// Permission is hereby granted, free of charge, to any person obtaining a
148.11 +// copy of this software and associated documentation files (the
148.12 +// "Software"), to deal in the Software without restriction, including
148.13 +// without limitation the rights to use, copy, modify, merge, publish,
148.14 +// distribute, sublicense, and/or sell copies of the Software, and to
148.15 +// permit persons to whom the Software is furnished to do so, subject to
148.16 +// the following conditions:
148.17 +//
148.18 +// The above copyright notice and this permission notice shall be included
148.19 +// in all copies or substantial portions of the Software.
148.20 +//
148.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
148.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
148.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
148.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
148.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
148.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
148.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
148.28 +// </copyright>
148.29 +// <summary>
148.30 +// Represents a report.
148.31 +// </summary>
148.32 +// --------------------------------------------------------------------------------------------------------------------
148.33 +namespace OxyPlot.Reporting
148.34 +{
148.35 + using System.Globalization;
148.36 +
148.37 + /// <summary>
148.38 + /// Represents a report.
148.39 + /// </summary>
148.40 + public class Report : ReportItem
148.41 + {
148.42 + /// <summary>
148.43 + /// Gets the actual culture.
148.44 + /// </summary>
148.45 + public CultureInfo ActualCulture
148.46 + {
148.47 + get
148.48 + {
148.49 + return this.Culture ?? CultureInfo.CurrentCulture;
148.50 + }
148.51 + }
148.52 +
148.53 + /// <summary>
148.54 + /// Gets or sets Author.
148.55 + /// </summary>
148.56 + public string Author { get; set; }
148.57 +
148.58 + /// <summary>
148.59 + /// Gets or sets the culture.
148.60 + /// </summary>
148.61 + /// <value>
148.62 + /// The culture.
148.63 + /// </value>
148.64 + public CultureInfo Culture { get; set; }
148.65 +
148.66 + /// <summary>
148.67 + /// Gets or sets SubTitle.
148.68 + /// </summary>
148.69 + public string SubTitle { get; set; }
148.70 +
148.71 + /// <summary>
148.72 + /// Gets or sets Title.
148.73 + /// </summary>
148.74 + public string Title { get; set; }
148.75 +
148.76 + /// <summary>
148.77 + /// The write.
148.78 + /// </summary>
148.79 + /// <param name="w">
148.80 + /// The w.
148.81 + /// </param>
148.82 + public override void Write(IReportWriter w)
148.83 + {
148.84 + this.UpdateParent(this);
148.85 + this.UpdateFigureNumbers();
148.86 + base.Write(w);
148.87 + }
148.88 +
148.89 + }
148.90 +}
148.91 \ No newline at end of file
149.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
149.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/ReportItem.cs Sat Jun 08 16:53:22 2013 +0000
149.3 @@ -0,0 +1,311 @@
149.4 +// --------------------------------------------------------------------------------------------------------------------
149.5 +// <copyright file="ReportItem.cs" company="OxyPlot">
149.6 +// The MIT License (MIT)
149.7 +//
149.8 +// Copyright (c) 2012 Oystein Bjorke
149.9 +//
149.10 +// Permission is hereby granted, free of charge, to any person obtaining a
149.11 +// copy of this software and associated documentation files (the
149.12 +// "Software"), to deal in the Software without restriction, including
149.13 +// without limitation the rights to use, copy, modify, merge, publish,
149.14 +// distribute, sublicense, and/or sell copies of the Software, and to
149.15 +// permit persons to whom the Software is furnished to do so, subject to
149.16 +// the following conditions:
149.17 +//
149.18 +// The above copyright notice and this permission notice shall be included
149.19 +// in all copies or substantial portions of the Software.
149.20 +//
149.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
149.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
149.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
149.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
149.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
149.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
149.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
149.28 +// </copyright>
149.29 +// <summary>
149.30 +// Represents a report item (abstract base class).
149.31 +// </summary>
149.32 +// --------------------------------------------------------------------------------------------------------------------
149.33 +namespace OxyPlot.Reporting
149.34 +{
149.35 + using System.Collections;
149.36 + using System.Collections.Generic;
149.37 + using System.Collections.ObjectModel;
149.38 +
149.39 + /// <summary>
149.40 + /// Represents a report item (abstract base class).
149.41 + /// </summary>
149.42 + public abstract class ReportItem
149.43 + {
149.44 + /// <summary>
149.45 + /// Initializes a new instance of the <see cref = "ReportItem" /> class.
149.46 + /// </summary>
149.47 + protected ReportItem()
149.48 + {
149.49 + this.Children = new Collection<ReportItem>();
149.50 + }
149.51 +
149.52 + /// <summary>
149.53 + /// Gets the children.
149.54 + /// </summary>
149.55 + public Collection<ReportItem> Children { get; private set; }
149.56 +
149.57 + /// <summary>
149.58 + /// Gets the report.
149.59 + /// </summary>
149.60 + public Report Report { get; internal set; }
149.61 +
149.62 + /// <summary>
149.63 + /// Adds a report item to the report.
149.64 + /// </summary>
149.65 + /// <param name="child">
149.66 + /// The child.
149.67 + /// </param>
149.68 + public void Add(ReportItem child)
149.69 + {
149.70 + this.Children.Add(child);
149.71 + }
149.72 +
149.73 + /// <summary>
149.74 + /// Adds a drawing to the report.
149.75 + /// </summary>
149.76 + /// <param name="content">
149.77 + /// The content.
149.78 + /// </param>
149.79 + /// <param name="text">
149.80 + /// The text.
149.81 + /// </param>
149.82 + public void AddDrawing(string content, string text)
149.83 + {
149.84 + this.Add(new DrawingFigure { Content = content, FigureText = text });
149.85 + }
149.86 +
149.87 + /// <summary>
149.88 + /// Adds a plot to the report.
149.89 + /// </summary>
149.90 + /// <param name="plot">The plot model.</param>
149.91 + /// <param name="text">The text.</param>
149.92 + /// <param name="width">The width.</param>
149.93 + /// <param name="height">The height.</param>
149.94 + public void AddPlot(PlotModel plot, string text, double width, double height)
149.95 + {
149.96 + this.Add(new PlotFigure { PlotModel = plot, Width = width, Height = height, FigureText = text });
149.97 + }
149.98 +
149.99 + /// <summary>
149.100 + /// Adds an equation to the report.
149.101 + /// </summary>
149.102 + /// <param name="equation">
149.103 + /// The equation.
149.104 + /// </param>
149.105 + /// <param name="caption">
149.106 + /// The caption.
149.107 + /// </param>
149.108 + public void AddEquation(string equation, string caption = null)
149.109 + {
149.110 + this.Add(new Equation { Content = equation, Caption = caption });
149.111 + }
149.112 +
149.113 + /// <summary>
149.114 + /// Adds a header to the report.
149.115 + /// </summary>
149.116 + /// <param name="level">
149.117 + /// The level.
149.118 + /// </param>
149.119 + /// <param name="header">
149.120 + /// The header.
149.121 + /// </param>
149.122 + public void AddHeader(int level, string header)
149.123 + {
149.124 + this.Add(new Header { Level = level, Text = header });
149.125 + }
149.126 +
149.127 + /// <summary>
149.128 + /// Adds an image to the report.
149.129 + /// </summary>
149.130 + /// <param name="src">
149.131 + /// The src.
149.132 + /// </param>
149.133 + /// <param name="text">
149.134 + /// The text.
149.135 + /// </param>
149.136 + public void AddImage(string src, string text)
149.137 + {
149.138 + this.Add(new Image { Source = src, FigureText = text });
149.139 + }
149.140 +
149.141 + /// <summary>
149.142 + /// Adds an items table to the report.
149.143 + /// </summary>
149.144 + /// <param name="title">
149.145 + /// The title.
149.146 + /// </param>
149.147 + /// <param name="items">
149.148 + /// The items.
149.149 + /// </param>
149.150 + /// <param name="fields">
149.151 + /// The fields.
149.152 + /// </param>
149.153 + public void AddItemsTable(string title, IEnumerable items, IList<ItemsTableField> fields)
149.154 + {
149.155 + this.Add(new ItemsTable { Caption = title, Items = items, Fields = fields });
149.156 + }
149.157 +
149.158 + /// <summary>
149.159 + /// Adds a paragraph to the report.
149.160 + /// </summary>
149.161 + /// <param name="content">
149.162 + /// The content.
149.163 + /// </param>
149.164 + public void AddParagraph(string content)
149.165 + {
149.166 + this.Add(new Paragraph { Text = content });
149.167 + }
149.168 +
149.169 + /// <summary>
149.170 + /// Adds a property table to the report.
149.171 + /// </summary>
149.172 + /// <param name="title">
149.173 + /// The title.
149.174 + /// </param>
149.175 + /// <param name="obj">
149.176 + /// The object.
149.177 + /// </param>
149.178 + /// <returns>
149.179 + /// A PropertyTable.
149.180 + /// </returns>
149.181 + public PropertyTable AddPropertyTable(string title, object obj)
149.182 + {
149.183 + var items = obj as IEnumerable;
149.184 + if (items == null)
149.185 + {
149.186 + items = new[] { obj };
149.187 + }
149.188 +
149.189 + var pt = new PropertyTable(items, false) { Caption = title };
149.190 + this.Add(pt);
149.191 + return pt;
149.192 + }
149.193 +
149.194 + /// <summary>
149.195 + /// The add table of contents.
149.196 + /// </summary>
149.197 + /// <param name="b">
149.198 + /// The b.
149.199 + /// </param>
149.200 + public void AddTableOfContents(ReportItem b)
149.201 + {
149.202 + this.Add(new TableOfContents(b));
149.203 + }
149.204 +
149.205 + /// <summary>
149.206 + /// The update.
149.207 + /// </summary>
149.208 + public virtual void Update()
149.209 + {
149.210 + }
149.211 +
149.212 + /// <summary>
149.213 + /// The write.
149.214 + /// </summary>
149.215 + /// <param name="w">
149.216 + /// The w.
149.217 + /// </param>
149.218 + public virtual void Write(IReportWriter w)
149.219 + {
149.220 + this.Update();
149.221 + this.WriteContent(w);
149.222 + foreach (var child in this.Children)
149.223 + {
149.224 + child.Write(w);
149.225 + }
149.226 + }
149.227 +
149.228 + /// <summary>
149.229 + /// Writes the content of the item.
149.230 + /// </summary>
149.231 + /// <param name="w">
149.232 + /// The writer.
149.233 + /// </param>
149.234 + public virtual void WriteContent(IReportWriter w)
149.235 + {
149.236 + }
149.237 +
149.238 + /// <summary>
149.239 + /// The update figure numbers.
149.240 + /// </summary>
149.241 + protected void UpdateFigureNumbers()
149.242 + {
149.243 + var fc = new FigureCounter();
149.244 + this.UpdateFigureNumbers(fc);
149.245 + }
149.246 +
149.247 + /// <summary>
149.248 + /// Updates the Report property.
149.249 + /// </summary>
149.250 + /// <param name="report">
149.251 + /// The report.
149.252 + /// </param>
149.253 + protected void UpdateParent(Report report)
149.254 + {
149.255 + this.Report = report;
149.256 + foreach (var child in this.Children)
149.257 + {
149.258 + child.UpdateParent(report);
149.259 + }
149.260 + }
149.261 +
149.262 + /// <summary>
149.263 + /// The update figure numbers.
149.264 + /// </summary>
149.265 + /// <param name="fc">
149.266 + /// The fc.
149.267 + /// </param>
149.268 + private void UpdateFigureNumbers(FigureCounter fc)
149.269 + {
149.270 + var table = this as Table;
149.271 + if (table != null)
149.272 + {
149.273 + table.TableNumber = fc.TableNumber++;
149.274 + }
149.275 +
149.276 + var figure = this as Figure;
149.277 + if (figure != null)
149.278 + {
149.279 + figure.FigureNumber = fc.FigureNumber++;
149.280 + }
149.281 +
149.282 + foreach (var child in this.Children)
149.283 + {
149.284 + child.UpdateFigureNumbers(fc);
149.285 + }
149.286 + }
149.287 +
149.288 + /// <summary>
149.289 + /// The figure counter.
149.290 + /// </summary>
149.291 + private class FigureCounter
149.292 + {
149.293 + /// <summary>
149.294 + /// Initializes a new instance of the <see cref = "FigureCounter" /> class.
149.295 + /// </summary>
149.296 + public FigureCounter()
149.297 + {
149.298 + this.FigureNumber = 1;
149.299 + this.TableNumber = 1;
149.300 + }
149.301 +
149.302 + /// <summary>
149.303 + /// Gets or sets FigureNumber.
149.304 + /// </summary>
149.305 + public int FigureNumber { get; set; }
149.306 +
149.307 + /// <summary>
149.308 + /// Gets or sets TableNumber.
149.309 + /// </summary>
149.310 + public int TableNumber { get; set; }
149.311 +
149.312 + }
149.313 + }
149.314 +}
149.315 \ No newline at end of file
150.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
150.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/ReportSection.cs Sat Jun 08 16:53:22 2013 +0000
150.3 @@ -0,0 +1,38 @@
150.4 +// --------------------------------------------------------------------------------------------------------------------
150.5 +// <copyright file="ReportSection.cs" company="OxyPlot">
150.6 +// The MIT License (MIT)
150.7 +//
150.8 +// Copyright (c) 2012 Oystein Bjorke
150.9 +//
150.10 +// Permission is hereby granted, free of charge, to any person obtaining a
150.11 +// copy of this software and associated documentation files (the
150.12 +// "Software"), to deal in the Software without restriction, including
150.13 +// without limitation the rights to use, copy, modify, merge, publish,
150.14 +// distribute, sublicense, and/or sell copies of the Software, and to
150.15 +// permit persons to whom the Software is furnished to do so, subject to
150.16 +// the following conditions:
150.17 +//
150.18 +// The above copyright notice and this permission notice shall be included
150.19 +// in all copies or substantial portions of the Software.
150.20 +//
150.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
150.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
150.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
150.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
150.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
150.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
150.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
150.28 +// </copyright>
150.29 +// <summary>
150.30 +// Represents a report section.
150.31 +// </summary>
150.32 +// --------------------------------------------------------------------------------------------------------------------
150.33 +namespace OxyPlot.Reporting
150.34 +{
150.35 + /// <summary>
150.36 + /// Represents a report section.
150.37 + /// </summary>
150.38 + public class ReportSection : ReportItem
150.39 + {
150.40 + }
150.41 +}
150.42 \ No newline at end of file
151.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
151.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/ReportStyle.cs Sat Jun 08 16:53:22 2013 +0000
151.3 @@ -0,0 +1,156 @@
151.4 +// --------------------------------------------------------------------------------------------------------------------
151.5 +// <copyright file="ReportStyle.cs" company="OxyPlot">
151.6 +// The MIT License (MIT)
151.7 +//
151.8 +// Copyright (c) 2012 Oystein Bjorke
151.9 +//
151.10 +// Permission is hereby granted, free of charge, to any person obtaining a
151.11 +// copy of this software and associated documentation files (the
151.12 +// "Software"), to deal in the Software without restriction, including
151.13 +// without limitation the rights to use, copy, modify, merge, publish,
151.14 +// distribute, sublicense, and/or sell copies of the Software, and to
151.15 +// permit persons to whom the Software is furnished to do so, subject to
151.16 +// the following conditions:
151.17 +//
151.18 +// The above copyright notice and this permission notice shall be included
151.19 +// in all copies or substantial portions of the Software.
151.20 +//
151.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
151.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
151.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
151.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
151.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
151.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
151.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
151.28 +// </copyright>
151.29 +// <summary>
151.30 +// The report style.
151.31 +// </summary>
151.32 +// --------------------------------------------------------------------------------------------------------------------
151.33 +namespace OxyPlot.Reporting
151.34 +{
151.35 + /// <summary>
151.36 + /// The report style.
151.37 + /// </summary>
151.38 + public class ReportStyle
151.39 + {
151.40 + /// <summary>
151.41 + /// Initializes a new instance of the <see cref="ReportStyle"/> class.
151.42 + /// </summary>
151.43 + /// <param name="titleFontFamily">
151.44 + /// The title font family.
151.45 + /// </param>
151.46 + /// <param name="bodyTextFontFamily">
151.47 + /// The body text font family.
151.48 + /// </param>
151.49 + /// <param name="tableTextFontFamily">
151.50 + /// The table text font family.
151.51 + /// </param>
151.52 + public ReportStyle(
151.53 + string titleFontFamily = "Arial",
151.54 + string bodyTextFontFamily = "Verdana",
151.55 + string tableTextFontFamily = "Courier New")
151.56 + {
151.57 + this.DefaultStyle = new ParagraphStyle { FontFamily = bodyTextFontFamily, FontSize = 11, SpacingAfter = 10 };
151.58 +
151.59 + this.HeaderStyles = new ParagraphStyle[5];
151.60 + this.HeaderStyles[0] = new ParagraphStyle
151.61 + {
151.62 + BasedOn = this.DefaultStyle, FontFamily = titleFontFamily, SpacingBefore = 12, SpacingAfter = 3
151.63 + };
151.64 + for (int i = 1; i < this.HeaderStyles.Length; i++)
151.65 + {
151.66 + this.HeaderStyles[i] = new ParagraphStyle { BasedOn = this.HeaderStyles[i - 1] };
151.67 + }
151.68 +
151.69 + for (int i = 0; i < this.HeaderStyles.Length; i++)
151.70 + {
151.71 + this.HeaderStyles[i].Bold = true;
151.72 + }
151.73 +
151.74 + this.HeaderStyles[0].FontSize = 16;
151.75 + this.HeaderStyles[1].FontSize = 14;
151.76 + this.HeaderStyles[2].FontSize = 13;
151.77 + this.HeaderStyles[3].FontSize = 12;
151.78 + this.HeaderStyles[4].FontSize = 11;
151.79 +
151.80 + this.HeaderStyles[0].PageBreakBefore = true;
151.81 + this.HeaderStyles[1].PageBreakBefore = false;
151.82 +
151.83 + this.BodyTextStyle = new ParagraphStyle { BasedOn = this.DefaultStyle };
151.84 + this.FigureTextStyle = new ParagraphStyle { BasedOn = this.DefaultStyle, Italic = true };
151.85 +
151.86 + this.TableTextStyle = new ParagraphStyle
151.87 + {
151.88 + BasedOn = this.DefaultStyle,
151.89 + FontFamily = tableTextFontFamily,
151.90 + SpacingAfter = 0,
151.91 + LeftIndentation = 3,
151.92 + RightIndentation = 3
151.93 + };
151.94 + this.TableHeaderStyle = new ParagraphStyle { BasedOn = this.TableTextStyle, Bold = true };
151.95 + this.TableCaptionStyle = new ParagraphStyle
151.96 + {
151.97 + BasedOn = this.DefaultStyle, Italic = true, SpacingBefore = 10, SpacingAfter = 3
151.98 + };
151.99 +
151.100 + this.Margins = new OxyThickness(25);
151.101 +
151.102 + this.FigureTextFormatString = "Figure {0}. {1}";
151.103 + this.TableCaptionFormatString = "Table {0}. {1}";
151.104 + }
151.105 +
151.106 + /// <summary>
151.107 + /// Gets or sets BodyTextStyle.
151.108 + /// </summary>
151.109 + public ParagraphStyle BodyTextStyle { get; set; }
151.110 +
151.111 + /// <summary>
151.112 + /// Gets or sets DefaultStyle.
151.113 + /// </summary>
151.114 + public ParagraphStyle DefaultStyle { get; set; }
151.115 +
151.116 + /// <summary>
151.117 + /// Gets or sets FigureTextFormatString.
151.118 + /// </summary>
151.119 + public string FigureTextFormatString { get; set; }
151.120 +
151.121 + /// <summary>
151.122 + /// Gets or sets FigureTextStyle.
151.123 + /// </summary>
151.124 + public ParagraphStyle FigureTextStyle { get; set; }
151.125 +
151.126 + /// <summary>
151.127 + /// Gets or sets HeaderStyles.
151.128 + /// </summary>
151.129 + public ParagraphStyle[] HeaderStyles { get; set; }
151.130 +
151.131 + /// <summary>
151.132 + /// Gets or sets the page margins (mm).
151.133 + /// </summary>
151.134 + public OxyThickness Margins { get; set; }
151.135 +
151.136 + // todo: should the FormatStrings be in the Report class?
151.137 +
151.138 + /// <summary>
151.139 + /// Gets or sets TableCaptionFormatString.
151.140 + /// </summary>
151.141 + public string TableCaptionFormatString { get; set; }
151.142 +
151.143 + /// <summary>
151.144 + /// Gets or sets TableCaptionStyle.
151.145 + /// </summary>
151.146 + public ParagraphStyle TableCaptionStyle { get; set; }
151.147 +
151.148 + /// <summary>
151.149 + /// Gets or sets TableHeaderStyle.
151.150 + /// </summary>
151.151 + public ParagraphStyle TableHeaderStyle { get; set; }
151.152 +
151.153 + /// <summary>
151.154 + /// Gets or sets TableTextStyle.
151.155 + /// </summary>
151.156 + public ParagraphStyle TableTextStyle { get; set; }
151.157 +
151.158 + }
151.159 +}
151.160 \ No newline at end of file
152.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
152.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/Table.cs Sat Jun 08 16:53:22 2013 +0000
152.3 @@ -0,0 +1,252 @@
152.4 +// --------------------------------------------------------------------------------------------------------------------
152.5 +// <copyright file="Table.cs" company="OxyPlot">
152.6 +// The MIT License (MIT)
152.7 +//
152.8 +// Copyright (c) 2012 Oystein Bjorke
152.9 +//
152.10 +// Permission is hereby granted, free of charge, to any person obtaining a
152.11 +// copy of this software and associated documentation files (the
152.12 +// "Software"), to deal in the Software without restriction, including
152.13 +// without limitation the rights to use, copy, modify, merge, publish,
152.14 +// distribute, sublicense, and/or sell copies of the Software, and to
152.15 +// permit persons to whom the Software is furnished to do so, subject to
152.16 +// the following conditions:
152.17 +//
152.18 +// The above copyright notice and this permission notice shall be included
152.19 +// in all copies or substantial portions of the Software.
152.20 +//
152.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
152.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
152.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
152.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
152.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
152.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
152.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
152.28 +// </copyright>
152.29 +// <summary>
152.30 +// Represents a table column definition.
152.31 +// </summary>
152.32 +// --------------------------------------------------------------------------------------------------------------------
152.33 +namespace OxyPlot.Reporting
152.34 +{
152.35 + using System;
152.36 + using System.Collections.Generic;
152.37 +
152.38 + /// <summary>
152.39 + /// Represents a table column definition.
152.40 + /// </summary>
152.41 + public class TableColumn
152.42 + {
152.43 + /// <summary>
152.44 + /// Initializes a new instance of the <see cref = "TableColumn" /> class.
152.45 + /// </summary>
152.46 + public TableColumn()
152.47 + {
152.48 + this.Width = double.NaN;
152.49 + this.Alignment = Alignment.Center;
152.50 + }
152.51 +
152.52 + /// <summary>
152.53 + /// Gets or sets the actual width (mm).
152.54 + /// </summary>
152.55 + /// <value>The actual width.</value>
152.56 + public double ActualWidth { get; internal set; }
152.57 +
152.58 + /// <summary>
152.59 + /// Gets or sets Alignment.
152.60 + /// </summary>
152.61 + public Alignment Alignment { get; set; }
152.62 +
152.63 + /// <summary>
152.64 + /// Gets or sets a value indicating whether IsHeader.
152.65 + /// </summary>
152.66 + public bool IsHeader { get; set; }
152.67 +
152.68 + /// <summary>
152.69 + /// Gets or sets the width.
152.70 + /// NaN: auto width.
152.71 + /// Negative numbers: weights
152.72 + /// </summary>
152.73 + /// <value>The width.</value>
152.74 + public double Width { get; set; }
152.75 +
152.76 + }
152.77 +
152.78 + /// <summary>
152.79 + /// Represents a table row definition.
152.80 + /// </summary>
152.81 + public class TableRow
152.82 + {
152.83 + /// <summary>
152.84 + /// Initializes a new instance of the <see cref = "TableRow" /> class.
152.85 + /// </summary>
152.86 + public TableRow()
152.87 + {
152.88 + this.Cells = new List<TableCell>();
152.89 + }
152.90 +
152.91 + /// <summary>
152.92 + /// Gets Cells.
152.93 + /// </summary>
152.94 + public IList<TableCell> Cells { get; private set; }
152.95 +
152.96 + /// <summary>
152.97 + /// Gets or sets a value indicating whether IsHeader.
152.98 + /// </summary>
152.99 + public bool IsHeader { get; set; }
152.100 +
152.101 + }
152.102 +
152.103 + /// <summary>
152.104 + /// Represents a table cell.
152.105 + /// </summary>
152.106 + public class TableCell
152.107 + {
152.108 + // public Alignment Alignment { get; set; }
152.109 + // public int RowSpan { get; set; }
152.110 + // public int ColumnSpan { get; set; }
152.111 + /// <summary>
152.112 + /// Gets or sets Content.
152.113 + /// </summary>
152.114 + public string Content { get; set; }
152.115 +
152.116 + }
152.117 +
152.118 + /// <summary>
152.119 + /// Represents a table.
152.120 + /// </summary>
152.121 + public class Table : ReportItem
152.122 + {
152.123 + /// <summary>
152.124 + /// Initializes a new instance of the <see cref = "Table" /> class.
152.125 + /// </summary>
152.126 + public Table()
152.127 + {
152.128 + this.Rows = new List<TableRow>();
152.129 + this.Columns = new List<TableColumn>();
152.130 + this.Width = double.NaN;
152.131 + }
152.132 +
152.133 + /// <summary>
152.134 + /// Gets or sets the actual width of the table (mm).
152.135 + /// </summary>
152.136 + /// <value>The actual width.</value>
152.137 + public double ActualWidth { get; private set; }
152.138 +
152.139 + /// <summary>
152.140 + /// Gets or sets Caption.
152.141 + /// </summary>
152.142 + public string Caption { get; set; }
152.143 +
152.144 + /// <summary>
152.145 + /// Gets Columns.
152.146 + /// </summary>
152.147 + public IList<TableColumn> Columns { get; private set; }
152.148 +
152.149 + /// <summary>
152.150 + /// Gets Rows.
152.151 + /// </summary>
152.152 + public IList<TableRow> Rows { get; private set; }
152.153 +
152.154 + /// <summary>
152.155 + /// Gets or sets TableNumber.
152.156 + /// </summary>
152.157 + public int TableNumber { get; set; }
152.158 +
152.159 + /// <summary>
152.160 + /// Gets or sets the width of the table (mm).
152.161 + /// NaN: auto width.
152.162 + /// 0..-1: fraction of page width.
152.163 + /// </summary>
152.164 + public double Width { get; set; }
152.165 +
152.166 + /// <summary>
152.167 + /// The get full caption.
152.168 + /// </summary>
152.169 + /// <param name="style">
152.170 + /// The style.
152.171 + /// </param>
152.172 + /// <returns>
152.173 + /// The get full caption.
152.174 + /// </returns>
152.175 + public string GetFullCaption(ReportStyle style)
152.176 + {
152.177 + return string.Format(style.TableCaptionFormatString, this.TableNumber, this.Caption);
152.178 + }
152.179 +
152.180 + /// <summary>
152.181 + /// The update.
152.182 + /// </summary>
152.183 + public override void Update()
152.184 + {
152.185 + base.Update();
152.186 + this.UpdateWidths();
152.187 + }
152.188 +
152.189 + /// <summary>
152.190 + /// The write content.
152.191 + /// </summary>
152.192 + /// <param name="w">
152.193 + /// The w.
152.194 + /// </param>
152.195 + public override void WriteContent(IReportWriter w)
152.196 + {
152.197 + // todo
152.198 + }
152.199 +
152.200 + /// <summary>
152.201 + /// The update widths.
152.202 + /// </summary>
152.203 + private void UpdateWidths()
152.204 + {
152.205 + if (this.Width < 0)
152.206 + {
152.207 + this.ActualWidth = 150 * (-this.Width);
152.208 + }
152.209 + else
152.210 + {
152.211 + this.ActualWidth = this.Width;
152.212 + }
152.213 +
152.214 + // update actual widths of all columns
152.215 + double totalWeight = 0;
152.216 + double totalWidth = 0;
152.217 + foreach (var c in this.Columns)
152.218 + {
152.219 + if (double.IsNaN(c.Width))
152.220 + {
152.221 + // todo: find auto width
152.222 + c.ActualWidth = 40;
152.223 + totalWidth += c.ActualWidth;
152.224 + }
152.225 +
152.226 + if (c.Width < 0)
152.227 + {
152.228 + totalWeight += -c.Width;
152.229 + }
152.230 +
152.231 + if (c.Width >= 0)
152.232 + {
152.233 + totalWidth += c.Width;
152.234 + c.ActualWidth = c.Width;
152.235 + }
152.236 + }
152.237 +
152.238 + if (double.IsNaN(this.ActualWidth))
152.239 + {
152.240 + this.ActualWidth = Math.Max(150, totalWidth + 100);
152.241 + }
152.242 +
152.243 + double w = this.ActualWidth - totalWidth;
152.244 + foreach (var c in this.Columns)
152.245 + {
152.246 + if (c.Width < 0 && totalWeight != 0)
152.247 + {
152.248 + double weight = -c.Width;
152.249 + c.ActualWidth = w * (weight / totalWeight);
152.250 + }
152.251 + }
152.252 + }
152.253 +
152.254 + }
152.255 +}
152.256 \ No newline at end of file
153.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
153.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/TableColumn.cs Sat Jun 08 16:53:22 2013 +0000
153.3 @@ -0,0 +1,63 @@
153.4 +// --------------------------------------------------------------------------------------------------------------------
153.5 +// <copyright file="TableColumn.cs" company="OxyPlot">
153.6 +// The MIT License (MIT)
153.7 +//
153.8 +// Copyright (c) 2012 Oystein Bjorke
153.9 +//
153.10 +// Permission is hereby granted, free of charge, to any person obtaining a
153.11 +// copy of this software and associated documentation files (the
153.12 +// "Software"), to deal in the Software without restriction, including
153.13 +// without limitation the rights to use, copy, modify, merge, publish,
153.14 +// distribute, sublicense, and/or sell copies of the Software, and to
153.15 +// permit persons to whom the Software is furnished to do so, subject to
153.16 +// the following conditions:
153.17 +//
153.18 +// The above copyright notice and this permission notice shall be included
153.19 +// in all copies or substantial portions of the Software.
153.20 +//
153.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
153.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
153.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
153.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
153.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
153.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
153.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
153.28 +// </copyright>
153.29 +// --------------------------------------------------------------------------------------------------------------------
153.30 +using System;
153.31 +using System.Collections.ObjectModel;
153.32 +using System.Globalization;
153.33 +
153.34 +namespace OxyPlot.Reporting
153.35 +{
153.36 + public enum Alignment { Left, Right, Center };
153.37 +
153.38 + public class TableColumn
153.39 + {
153.40 + public Alignment Alignment { get; set; }
153.41 + public string Header { get; set; }
153.42 + public string StringFormat { get; set; }
153.43 + public string Path { get; set; }
153.44 + public double Width { get; set; }
153.45 + // public Collection<TableColumn> SubColumns { get; set; }
153.46 +
153.47 + public TableColumn(string header, string path, string stringFormat=null, Alignment alignment=Alignment.Center)
153.48 + {
153.49 + Header = header;
153.50 + Path = path;
153.51 + StringFormat = stringFormat;
153.52 + Alignment = alignment;
153.53 + // SubColumns = new Collection<TableColumn>();
153.54 + }
153.55 +
153.56 + public string GetText(object item)
153.57 + {
153.58 + var pi = item.GetType().GetProperty(Path);
153.59 + object o = pi.GetValue(item, null);
153.60 + var of = o as IFormattable;
153.61 + if (of != null)
153.62 + return of.ToString(StringFormat, CultureInfo.InvariantCulture);
153.63 + return o!=null ? o.ToString():null;
153.64 + }
153.65 + }
153.66 +}
153.67 \ No newline at end of file
154.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
154.2 +++ b/External/OxyPlot/OxyPlot/Reporting/Report/TableOfContents.cs Sat Jun 08 16:53:22 2013 +0000
154.3 @@ -0,0 +1,115 @@
154.4 +// --------------------------------------------------------------------------------------------------------------------
154.5 +// <copyright file="TableOfContents.cs" company="OxyPlot">
154.6 +// The MIT License (MIT)
154.7 +//
154.8 +// Copyright (c) 2012 Oystein Bjorke
154.9 +//
154.10 +// Permission is hereby granted, free of charge, to any person obtaining a
154.11 +// copy of this software and associated documentation files (the
154.12 +// "Software"), to deal in the Software without restriction, including
154.13 +// without limitation the rights to use, copy, modify, merge, publish,
154.14 +// distribute, sublicense, and/or sell copies of the Software, and to
154.15 +// permit persons to whom the Software is furnished to do so, subject to
154.16 +// the following conditions:
154.17 +//
154.18 +// The above copyright notice and this permission notice shall be included
154.19 +// in all copies or substantial portions of the Software.
154.20 +//
154.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
154.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
154.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
154.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
154.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
154.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
154.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
154.28 +// </copyright>
154.29 +// <summary>
154.30 +// Represents a table of contents.
154.31 +// </summary>
154.32 +// --------------------------------------------------------------------------------------------------------------------
154.33 +namespace OxyPlot.Reporting
154.34 +{
154.35 + using System.Collections.Generic;
154.36 +
154.37 + /// <summary>
154.38 + /// Represents a table of contents.
154.39 + /// </summary>
154.40 + public class TableOfContents : ItemsTable
154.41 + {
154.42 + /// <summary>
154.43 + /// Initializes a new instance of the <see cref="TableOfContents"/> class.
154.44 + /// </summary>
154.45 + /// <param name="b">
154.46 + /// The b.
154.47 + /// </param>
154.48 + public TableOfContents(ReportItem b)
154.49 + {
154.50 + this.Base = b;
154.51 + this.Contents = new List<ContentItem>();
154.52 + this.Fields.Add(new ItemsTableField(null, "Chapter"));
154.53 + this.Fields.Add(new ItemsTableField(null, "Title"));
154.54 + this.Items = this.Contents;
154.55 + }
154.56 +
154.57 + /// <summary>
154.58 + /// Gets or sets Base.
154.59 + /// </summary>
154.60 + public ReportItem Base { get; set; }
154.61 +
154.62 + /// <summary>
154.63 + /// Gets or sets Contents.
154.64 + /// </summary>
154.65 + public List<ContentItem> Contents { get; set; }
154.66 +
154.67 + /// <summary>
154.68 + /// The update.
154.69 + /// </summary>
154.70 + public override void Update()
154.71 + {
154.72 + this.Contents.Clear();
154.73 + var hh = new HeaderHelper();
154.74 + this.Search(this.Base, hh);
154.75 + base.Update();
154.76 + }
154.77 +
154.78 + /// <summary>
154.79 + /// The search.
154.80 + /// </summary>
154.81 + /// <param name="item">
154.82 + /// The item.
154.83 + /// </param>
154.84 + /// <param name="hh">
154.85 + /// The hh.
154.86 + /// </param>
154.87 + private void Search(ReportItem item, HeaderHelper hh)
154.88 + {
154.89 + var h = item as Header;
154.90 + if (h != null)
154.91 + {
154.92 + h.Chapter = hh.GetHeader(h.Level);
154.93 + this.Contents.Add(new ContentItem { Chapter = h.Chapter, Title = h.Text });
154.94 + }
154.95 +
154.96 + foreach (var c in item.Children)
154.97 + {
154.98 + this.Search(c, hh);
154.99 + }
154.100 + }
154.101 +
154.102 + /// <summary>
154.103 + /// The content item.
154.104 + /// </summary>
154.105 + public class ContentItem
154.106 + {
154.107 + /// <summary>
154.108 + /// Gets or sets Chapter.
154.109 + /// </summary>
154.110 + public string Chapter { get; set; }
154.111 +
154.112 + /// <summary>
154.113 + /// Gets or sets Title.
154.114 + /// </summary>
154.115 + public string Title { get; set; }
154.116 + }
154.117 + }
154.118 +}
154.119 \ No newline at end of file
155.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
155.2 +++ b/External/OxyPlot/OxyPlot/Reporting/ReportWriters/HtmlReportWriter.cs Sat Jun 08 16:53:22 2013 +0000
155.3 @@ -0,0 +1,501 @@
155.4 +// --------------------------------------------------------------------------------------------------------------------
155.5 +// <copyright file="HtmlReportWriter.cs" company="OxyPlot">
155.6 +// The MIT License (MIT)
155.7 +//
155.8 +// Copyright (c) 2012 Oystein Bjorke
155.9 +//
155.10 +// Permission is hereby granted, free of charge, to any person obtaining a
155.11 +// copy of this software and associated documentation files (the
155.12 +// "Software"), to deal in the Software without restriction, including
155.13 +// without limitation the rights to use, copy, modify, merge, publish,
155.14 +// distribute, sublicense, and/or sell copies of the Software, and to
155.15 +// permit persons to whom the Software is furnished to do so, subject to
155.16 +// the following conditions:
155.17 +//
155.18 +// The above copyright notice and this permission notice shall be included
155.19 +// in all copies or substantial portions of the Software.
155.20 +//
155.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
155.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
155.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
155.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
155.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
155.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
155.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
155.28 +// </copyright>
155.29 +// <summary>
155.30 +// Specifies the html element type to use when writing plots.
155.31 +// </summary>
155.32 +// --------------------------------------------------------------------------------------------------------------------
155.33 +namespace OxyPlot.Reporting
155.34 +{
155.35 + using System.Collections.Generic;
155.36 + using System.IO;
155.37 + using System.Text;
155.38 +
155.39 + /// <summary>
155.40 + /// Specifies the html element type to use when writing plots.
155.41 + /// </summary>
155.42 + public enum HtmlPlotElementType
155.43 + {
155.44 + /// <summary>
155.45 + /// Use the embed tag and reference an external svg file.
155.46 + /// </summary>
155.47 + Embed,
155.48 +
155.49 + /// <summary>
155.50 + /// Use the object tag and reference an external svg file.
155.51 + /// </summary>
155.52 + Object,
155.53 +
155.54 + /// <summary>
155.55 + /// Use the svg tag and include the plot inline.
155.56 + /// </summary>
155.57 + Svg
155.58 + }
155.59 +
155.60 + /// <summary>
155.61 + /// HTML5 report writer.
155.62 + /// </summary>
155.63 + public class HtmlReportWriter : XmlWriterBase, IReportWriter
155.64 + {
155.65 + /// <summary>
155.66 + /// The text measurer.
155.67 + /// </summary>
155.68 + private readonly IRenderContext textMeasurer;
155.69 +
155.70 + /// <summary>
155.71 + /// The figure counter.
155.72 + /// </summary>
155.73 + private int figureCounter;
155.74 +
155.75 + /// <summary>
155.76 + /// The style.
155.77 + /// </summary>
155.78 + private ReportStyle style;
155.79 +
155.80 + /// <summary>
155.81 + /// Initializes a new instance of the <see cref="HtmlReportWriter"/> class.
155.82 + /// </summary>
155.83 + /// <param name="stream">
155.84 + /// The stream.
155.85 + /// </param>
155.86 + /// <param name="textMeasurer">
155.87 + /// The text measurer.
155.88 + /// </param>
155.89 + public HtmlReportWriter(Stream stream, IRenderContext textMeasurer = null)
155.90 + : base(stream)
155.91 + {
155.92 + this.textMeasurer = textMeasurer;
155.93 + this.WriteHtmlElement();
155.94 + this.PlotElementType = HtmlPlotElementType.Svg;
155.95 + }
155.96 +
155.97 + /// <summary>
155.98 + /// Gets or sets the type of the plot element.
155.99 + /// </summary>
155.100 + /// <value>
155.101 + /// The type of the plot element.
155.102 + /// </value>
155.103 + public HtmlPlotElementType PlotElementType { get; set; }
155.104 +
155.105 + /// <summary>
155.106 + /// Closes this instance.
155.107 + /// </summary>
155.108 + public override void Close()
155.109 + {
155.110 + this.WriteEndElement();
155.111 + this.WriteEndElement();
155.112 + base.Close();
155.113 + }
155.114 +
155.115 + /// <summary>
155.116 + /// Writes the class ID.
155.117 + /// </summary>
155.118 + /// <param name="className">
155.119 + /// The class.
155.120 + /// </param>
155.121 + /// <param name="id">
155.122 + /// The id.
155.123 + /// </param>
155.124 + public void WriteClassId(string className, string id = null)
155.125 + {
155.126 + if (className != null)
155.127 + {
155.128 + this.WriteAttributeString("class", className);
155.129 + }
155.130 +
155.131 + if (id != null)
155.132 + {
155.133 + this.WriteAttributeString("id", id);
155.134 + }
155.135 + }
155.136 +
155.137 + /// <summary>
155.138 + /// Writes the drawing.
155.139 + /// </summary>
155.140 + /// <param name="d">
155.141 + /// The drawing.
155.142 + /// </param>
155.143 + public void WriteDrawing(DrawingFigure d)
155.144 + {
155.145 + this.WriteStartFigure();
155.146 + this.WriteRaw(d.Content);
155.147 + this.WriteEndFigure(d.FigureText);
155.148 + }
155.149 +
155.150 + /// <summary>
155.151 + /// Writes the equation.
155.152 + /// </summary>
155.153 + /// <param name="equation">
155.154 + /// The equation.
155.155 + /// </param>
155.156 + public void WriteEquation(Equation equation)
155.157 + {
155.158 + // todo: MathML?
155.159 + }
155.160 +
155.161 + /// <summary>
155.162 + /// Writes the header.
155.163 + /// </summary>
155.164 + /// <param name="h">
155.165 + /// The header.
155.166 + /// </param>
155.167 + public void WriteHeader(Header h)
155.168 + {
155.169 + if (h.Text == null)
155.170 + {
155.171 + return;
155.172 + }
155.173 +
155.174 + this.WriteStartElement("h" + h.Level);
155.175 + this.WriteString(h.ToString());
155.176 + this.WriteEndElement();
155.177 + }
155.178 +
155.179 + /// <summary>
155.180 + /// Writes the image.
155.181 + /// </summary>
155.182 + /// <param name="i">
155.183 + /// The image.
155.184 + /// </param>
155.185 + public void WriteImage(Image i)
155.186 + {
155.187 + // this requires the image to be located in the same folder as the html
155.188 + string localFileName = i.Source;
155.189 + this.WriteStartFigure();
155.190 + this.WriteStartElement("img");
155.191 + this.WriteAttributeString("src", localFileName);
155.192 + this.WriteAttributeString("alt", i.FigureText);
155.193 + this.WriteEndElement();
155.194 + this.WriteEndFigure(i.FigureText);
155.195 + }
155.196 +
155.197 + /// <summary>
155.198 + /// Writes the paragraph.
155.199 + /// </summary>
155.200 + /// <param name="p">
155.201 + /// The paragraph.
155.202 + /// </param>
155.203 + public void WriteParagraph(Paragraph p)
155.204 + {
155.205 + this.WriteElementString("p", p.Text);
155.206 + }
155.207 +
155.208 + /// <summary>
155.209 + /// Writes the plot.
155.210 + /// </summary>
155.211 + /// <param name="plot">
155.212 + /// The plot.
155.213 + /// </param>
155.214 + public void WritePlot(PlotFigure plot)
155.215 + {
155.216 + this.WriteStartFigure();
155.217 + switch (this.PlotElementType)
155.218 + {
155.219 + case HtmlPlotElementType.Embed:
155.220 + case HtmlPlotElementType.Object:
155.221 + // TODO: need a Func<string,Stream> to provide streams for the plot files?
155.222 +
155.223 + //string source = string.Format(
155.224 + // "{0}_Plot{1}.svg", Path.GetFileNameWithoutExtension(this.outputFile), plot.FigureNumber);
155.225 + //plot.PlotModel.SaveSvg(this.GetFullFileName(source), plot.Width, plot.Height, this.textMeasurer);
155.226 + //this.WriteStartElement(this.PlotElementType == HtmlPlotElementType.Embed ? "embed" : "object");
155.227 + //this.WriteAttributeString("src", source);
155.228 + //this.WriteAttributeString("type", "image/svg+xml");
155.229 + //this.WriteEndElement();
155.230 + break;
155.231 + case HtmlPlotElementType.Svg:
155.232 + this.WriteRaw(plot.PlotModel.ToSvg(plot.Width, plot.Height, false, this.textMeasurer));
155.233 + break;
155.234 + }
155.235 +
155.236 + this.WriteEndFigure(plot.FigureText);
155.237 + }
155.238 +
155.239 + /// <summary>
155.240 + /// The write report.
155.241 + /// </summary>
155.242 + /// <param name="report">
155.243 + /// The report.
155.244 + /// </param>
155.245 + /// <param name="reportStyle">
155.246 + /// The style.
155.247 + /// </param>
155.248 + public void WriteReport(Report report, ReportStyle reportStyle)
155.249 + {
155.250 + this.style = reportStyle;
155.251 + this.WriteHtmlHeader(report.Title, null, CreateCss(reportStyle));
155.252 + report.Write(this);
155.253 + }
155.254 +
155.255 + /// <summary>
155.256 + /// Writes the items.
155.257 + /// </summary>
155.258 + /// <param name="t">
155.259 + /// The table.
155.260 + /// </param>
155.261 + public void WriteRows(Table t)
155.262 + {
155.263 + IList<TableColumn> columns = t.Columns;
155.264 +
155.265 + foreach (var c in columns)
155.266 + {
155.267 + this.WriteStartElement("col");
155.268 + this.WriteAttributeString("align", GetAlignmentString(c.Alignment));
155.269 + if (double.IsNaN(c.Width))
155.270 + {
155.271 + this.WriteAttributeString("width", c.Width + "pt");
155.272 + }
155.273 +
155.274 + this.WriteEndElement();
155.275 + }
155.276 +
155.277 + foreach (var row in t.Rows)
155.278 + {
155.279 + if (row.IsHeader)
155.280 + {
155.281 + this.WriteStartElement("thead");
155.282 + }
155.283 +
155.284 + this.WriteStartElement("tr");
155.285 + int j = 0;
155.286 + foreach (var c in row.Cells)
155.287 + {
155.288 + bool isHeader = row.IsHeader || t.Columns[j++].IsHeader;
155.289 +
155.290 + this.WriteStartElement("td");
155.291 + if (isHeader)
155.292 + {
155.293 + this.WriteAttributeString("class", "header");
155.294 + }
155.295 +
155.296 + this.WriteString(c.Content);
155.297 + this.WriteEndElement();
155.298 + }
155.299 +
155.300 + this.WriteEndElement(); // tr
155.301 + if (row.IsHeader)
155.302 + {
155.303 + this.WriteEndElement(); // thead
155.304 + }
155.305 + }
155.306 + }
155.307 +
155.308 + /// <summary>
155.309 + /// Writes the table.
155.310 + /// </summary>
155.311 + /// <param name="t">
155.312 + /// The t.
155.313 + /// </param>
155.314 + public void WriteTable(Table t)
155.315 + {
155.316 + if (t.Rows == null || t.Columns == null)
155.317 + {
155.318 + return;
155.319 + }
155.320 +
155.321 + this.WriteStartElement("table");
155.322 +
155.323 + // WriteAttributeString("border", "1");
155.324 + // WriteAttributeString("width", "60%");
155.325 + if (t.Caption != null)
155.326 + {
155.327 + this.WriteStartElement("caption");
155.328 + this.WriteString(t.GetFullCaption(this.style));
155.329 + this.WriteEndElement();
155.330 + }
155.331 +
155.332 + this.WriteRows(t);
155.333 +
155.334 + this.WriteEndElement(); // table
155.335 + }
155.336 +
155.337 + /// <summary>
155.338 + /// Creates the css section.
155.339 + /// </summary>
155.340 + /// <param name="style">
155.341 + /// The style.
155.342 + /// </param>
155.343 + /// <returns>
155.344 + /// The css.
155.345 + /// </returns>
155.346 + private static string CreateCss(ReportStyle style)
155.347 + {
155.348 + var css = new StringBuilder();
155.349 + css.AppendLine("body { " + ParagraphStyleToCss(style.BodyTextStyle) + " }");
155.350 + for (int i = 0; i < style.HeaderStyles.Length; i++)
155.351 + {
155.352 + css.AppendLine("h" + (i + 1) + " {" + ParagraphStyleToCss(style.HeaderStyles[i]) + " }");
155.353 + }
155.354 +
155.355 + css.AppendLine("table caption { " + ParagraphStyleToCss(style.TableCaptionStyle) + " }");
155.356 + css.AppendLine("thead { " + ParagraphStyleToCss(style.TableHeaderStyle) + " }");
155.357 + css.AppendLine("td { " + ParagraphStyleToCss(style.TableTextStyle) + " }");
155.358 + css.AppendLine("td.header { " + ParagraphStyleToCss(style.TableHeaderStyle) + " }");
155.359 + css.AppendLine("figuretext { " + ParagraphStyleToCss(style.FigureTextStyle) + " }");
155.360 +
155.361 + css.Append(
155.362 + @"body { margin:20pt; }
155.363 + table { border: solid 1px black; margin: 8pt; border-collapse:collapse; }
155.364 + td { padding: 0 2pt 0 2pt; border-left: solid 1px black; border-right: solid 1px black;}
155.365 + thead { border:solid 1px black; }
155.366 + .content, .content td { border: none; }
155.367 + .figure { margin: 8pt;}
155.368 + .table { margin: 8pt;}
155.369 + .table caption { margin: 4pt;}
155.370 + .table thead td { padding: 2pt;}");
155.371 + return css.ToString();
155.372 + }
155.373 +
155.374 + /// <summary>
155.375 + /// Gets the alignment string.
155.376 + /// </summary>
155.377 + /// <param name="a">
155.378 + /// The alignment type.
155.379 + /// </param>
155.380 + /// <returns>
155.381 + /// An alignment string.
155.382 + /// </returns>
155.383 + private static string GetAlignmentString(Alignment a)
155.384 + {
155.385 + return a.ToString().ToLower();
155.386 + }
155.387 +
155.388 + /// <summary>
155.389 + /// Converts a paragraphes style to css.
155.390 + /// </summary>
155.391 + /// <param name="s">
155.392 + /// The style.
155.393 + /// </param>
155.394 + /// <returns>
155.395 + /// A css string.
155.396 + /// </returns>
155.397 + private static string ParagraphStyleToCss(ParagraphStyle s)
155.398 + {
155.399 + var css = new StringBuilder();
155.400 + if (s.FontFamily != null)
155.401 + {
155.402 + css.Append(string.Format("font-family:{0};", s.FontFamily));
155.403 + }
155.404 +
155.405 + css.Append(string.Format("font-size:{0}pt;", s.FontSize));
155.406 + if (s.Bold)
155.407 + {
155.408 + css.Append(string.Format("font-weight:bold;"));
155.409 + }
155.410 +
155.411 + return css.ToString();
155.412 + }
155.413 +
155.414 + /// <summary>
155.415 + /// Initializes this instance.
155.416 + /// </summary>
155.417 + private void WriteHtmlElement()
155.418 + {
155.419 + this.WriteStartElement("html", "http://www.w3.org/1999/xhtml");
155.420 + }
155.421 +
155.422 + /// <summary>
155.423 + /// Writes the div.
155.424 + /// </summary>
155.425 + /// <param name="divstyle">
155.426 + /// The style of the div.
155.427 + /// </param>
155.428 + /// <param name="content">
155.429 + /// The content.
155.430 + /// </param>
155.431 + private void WriteDiv(string divstyle, string content)
155.432 + {
155.433 + this.WriteStartElement("div");
155.434 + this.WriteAttributeString("class", divstyle);
155.435 + this.WriteString(content);
155.436 + this.WriteEndElement();
155.437 + }
155.438 +
155.439 + /// <summary>
155.440 + /// Writes the end figure.
155.441 + /// </summary>
155.442 + /// <param name="text">
155.443 + /// The figure text.
155.444 + /// </param>
155.445 + private void WriteEndFigure(string text)
155.446 + {
155.447 + this.WriteDiv("figuretext", string.Format("Fig {0}. {1}", this.figureCounter, text));
155.448 + this.WriteEndElement();
155.449 + }
155.450 +
155.451 + /// <summary>
155.452 + /// Writes the HTML header.
155.453 + /// </summary>
155.454 + /// <param name="title">
155.455 + /// The title.
155.456 + /// </param>
155.457 + /// <param name="cssPath">
155.458 + /// The CSS path.
155.459 + /// </param>
155.460 + /// <param name="cssStyle">
155.461 + /// The style.
155.462 + /// </param>
155.463 + private void WriteHtmlHeader(string title, string cssPath, string cssStyle)
155.464 + {
155.465 + this.WriteStartElement("head");
155.466 +
155.467 + if (title != null)
155.468 + {
155.469 + this.WriteElementString("title", title);
155.470 + }
155.471 +
155.472 + if (cssPath != null)
155.473 + {
155.474 + this.WriteStartElement("link");
155.475 + this.WriteAttributeString("href", cssPath);
155.476 + this.WriteAttributeString("rel", "stylesheet");
155.477 + this.WriteAttributeString("type", "text/css");
155.478 + this.WriteEndElement(); // link
155.479 + }
155.480 +
155.481 + if (cssStyle != null)
155.482 + {
155.483 + this.WriteStartElement("style");
155.484 + this.WriteAttributeString("type", "text/css");
155.485 + this.WriteRaw(cssStyle);
155.486 + this.WriteEndElement();
155.487 + }
155.488 +
155.489 + this.WriteEndElement(); // head
155.490 + this.WriteStartElement("body");
155.491 + }
155.492 +
155.493 + /// <summary>
155.494 + /// Writes the start figure element.
155.495 + /// </summary>
155.496 + private void WriteStartFigure()
155.497 + {
155.498 + this.figureCounter++;
155.499 + this.WriteStartElement("p");
155.500 + this.WriteClassId("figure");
155.501 + }
155.502 +
155.503 + }
155.504 +}
155.505 \ No newline at end of file
156.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
156.2 +++ b/External/OxyPlot/OxyPlot/Reporting/ReportWriters/IReportWriter.cs Sat Jun 08 16:53:22 2013 +0000
156.3 @@ -0,0 +1,87 @@
156.4 +// --------------------------------------------------------------------------------------------------------------------
156.5 +// <copyright file="IReportWriter.cs" company="OxyPlot">
156.6 +// The MIT License (MIT)
156.7 +//
156.8 +// Copyright (c) 2012 Oystein Bjorke
156.9 +//
156.10 +// Permission is hereby granted, free of charge, to any person obtaining a
156.11 +// copy of this software and associated documentation files (the
156.12 +// "Software"), to deal in the Software without restriction, including
156.13 +// without limitation the rights to use, copy, modify, merge, publish,
156.14 +// distribute, sublicense, and/or sell copies of the Software, and to
156.15 +// permit persons to whom the Software is furnished to do so, subject to
156.16 +// the following conditions:
156.17 +//
156.18 +// The above copyright notice and this permission notice shall be included
156.19 +// in all copies or substantial portions of the Software.
156.20 +//
156.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
156.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
156.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
156.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
156.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
156.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
156.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
156.28 +// </copyright>
156.29 +// <summary>
156.30 +// Interface for Report writers.
156.31 +// </summary>
156.32 +// --------------------------------------------------------------------------------------------------------------------
156.33 +namespace OxyPlot.Reporting
156.34 +{
156.35 + /// <summary>
156.36 + /// Interface for Report writers.
156.37 + /// </summary>
156.38 + public interface IReportWriter
156.39 + {
156.40 + /// <summary>
156.41 + /// Writes the drawing.
156.42 + /// </summary>
156.43 + /// <param name="drawing">The drawing.</param>
156.44 + void WriteDrawing(DrawingFigure drawing);
156.45 +
156.46 + /// <summary>
156.47 + /// Writes the equation.
156.48 + /// </summary>
156.49 + /// <param name="equation">The equation.</param>
156.50 + void WriteEquation(Equation equation);
156.51 +
156.52 + /// <summary>
156.53 + /// Writes the header.
156.54 + /// </summary>
156.55 + /// <param name="header">The header.</param>
156.56 + void WriteHeader(Header header);
156.57 +
156.58 + /// <summary>
156.59 + /// Writes the image.
156.60 + /// </summary>
156.61 + /// <param name="image">The image.</param>
156.62 + void WriteImage(Image image);
156.63 +
156.64 + /// <summary>
156.65 + /// Writes the paragraph.
156.66 + /// </summary>
156.67 + /// <param name="paragraph">The paragraph.</param>
156.68 + void WriteParagraph(Paragraph paragraph);
156.69 +
156.70 + /// <summary>
156.71 + /// Writes the plot.
156.72 + /// </summary>
156.73 + /// <param name="plot">The plot.</param>
156.74 + void WritePlot(PlotFigure plot);
156.75 +
156.76 + /// <summary>
156.77 + /// Writes the report.
156.78 + /// </summary>
156.79 + /// <param name="report">The report.</param>
156.80 + /// <param name="reportStyle">The style.</param>
156.81 + void WriteReport(Report report, ReportStyle reportStyle);
156.82 +
156.83 + /// <summary>
156.84 + /// Writes the table.
156.85 + /// </summary>
156.86 + /// <param name="table">The table.</param>
156.87 + void WriteTable(Table table);
156.88 +
156.89 + }
156.90 +}
156.91 \ No newline at end of file
157.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
157.2 +++ b/External/OxyPlot/OxyPlot/Reporting/ReportWriters/StringExtensions.cs Sat Jun 08 16:53:22 2013 +0000
157.3 @@ -0,0 +1,130 @@
157.4 +// --------------------------------------------------------------------------------------------------------------------
157.5 +// <copyright file="StringExtensions.cs" company="OxyPlot">
157.6 +// The MIT License (MIT)
157.7 +//
157.8 +// Copyright (c) 2012 Oystein Bjorke
157.9 +//
157.10 +// Permission is hereby granted, free of charge, to any person obtaining a
157.11 +// copy of this software and associated documentation files (the
157.12 +// "Software"), to deal in the Software without restriction, including
157.13 +// without limitation the rights to use, copy, modify, merge, publish,
157.14 +// distribute, sublicense, and/or sell copies of the Software, and to
157.15 +// permit persons to whom the Software is furnished to do so, subject to
157.16 +// the following conditions:
157.17 +//
157.18 +// The above copyright notice and this permission notice shall be included
157.19 +// in all copies or substantial portions of the Software.
157.20 +//
157.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
157.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
157.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
157.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
157.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
157.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
157.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
157.28 +// </copyright>
157.29 +// <summary>
157.30 +// The string extensions.
157.31 +// </summary>
157.32 +// --------------------------------------------------------------------------------------------------------------------
157.33 +namespace OxyPlot.Reporting
157.34 +{
157.35 + using System.Collections.Generic;
157.36 + using System.Text;
157.37 +
157.38 + /// <summary>
157.39 + /// The string extensions.
157.40 + /// </summary>
157.41 + public static class StringExtensions
157.42 + {
157.43 + /// <summary>
157.44 + /// The repeat.
157.45 + /// </summary>
157.46 + /// <param name="source">
157.47 + /// The source.
157.48 + /// </param>
157.49 + /// <param name="n">
157.50 + /// The n.
157.51 + /// </param>
157.52 + /// <returns>
157.53 + /// The repeat.
157.54 + /// </returns>
157.55 + public static string Repeat(this string source, int n)
157.56 + {
157.57 + var sb = new StringBuilder(n * source.Length);
157.58 + for (int i = 0; i < n; i++)
157.59 + {
157.60 + sb.Append(source);
157.61 + }
157.62 +
157.63 + return sb.ToString();
157.64 + }
157.65 +
157.66 + /// <summary>
157.67 + /// The split lines.
157.68 + /// </summary>
157.69 + /// <param name="s">
157.70 + /// The s.
157.71 + /// </param>
157.72 + /// <param name="lineLength">
157.73 + /// The line length.
157.74 + /// </param>
157.75 + /// <returns>
157.76 + /// </returns>
157.77 + public static string[] SplitLines(this string s, int lineLength = 80)
157.78 + {
157.79 + var lines = new List<string>();
157.80 +
157.81 + int i = 0;
157.82 + while (i < s.Length)
157.83 + {
157.84 + int len = FindLineLength(s, i, lineLength);
157.85 + lines.Add(len == 0 ? s.Substring(i).Trim() : s.Substring(i, len).Trim());
157.86 + i += len;
157.87 + if (len == 0)
157.88 + {
157.89 + break;
157.90 + }
157.91 + }
157.92 +
157.93 + return lines.ToArray();
157.94 + }
157.95 +
157.96 + /// <summary>
157.97 + /// The find line length.
157.98 + /// </summary>
157.99 + /// <param name="text">
157.100 + /// The text.
157.101 + /// </param>
157.102 + /// <param name="i">
157.103 + /// The i.
157.104 + /// </param>
157.105 + /// <param name="maxLineLength">
157.106 + /// The max line length.
157.107 + /// </param>
157.108 + /// <returns>
157.109 + /// The find line length.
157.110 + /// </returns>
157.111 + private static int FindLineLength(string text, int i, int maxLineLength)
157.112 + {
157.113 + int i2 = i + 1;
157.114 + int len = 0;
157.115 + while (i2 < i + maxLineLength && i2 < text.Length)
157.116 + {
157.117 + i2 = text.IndexOfAny(" \n\r".ToCharArray(), i2 + 1);
157.118 + if (i2 == -1)
157.119 + {
157.120 + i2 = text.Length;
157.121 + }
157.122 +
157.123 + if (i2 - i < maxLineLength)
157.124 + {
157.125 + len = i2 - i;
157.126 + }
157.127 + }
157.128 +
157.129 + return len;
157.130 + }
157.131 +
157.132 + }
157.133 +}
157.134 \ No newline at end of file
158.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
158.2 +++ b/External/OxyPlot/OxyPlot/Reporting/ReportWriters/TextReportWriter.cs Sat Jun 08 16:53:22 2013 +0000
158.3 @@ -0,0 +1,289 @@
158.4 +// --------------------------------------------------------------------------------------------------------------------
158.5 +// <copyright file="TextReportWriter.cs" company="OxyPlot">
158.6 +// The MIT License (MIT)
158.7 +//
158.8 +// Copyright (c) 2012 Oystein Bjorke
158.9 +//
158.10 +// Permission is hereby granted, free of charge, to any person obtaining a
158.11 +// copy of this software and associated documentation files (the
158.12 +// "Software"), to deal in the Software without restriction, including
158.13 +// without limitation the rights to use, copy, modify, merge, publish,
158.14 +// distribute, sublicense, and/or sell copies of the Software, and to
158.15 +// permit persons to whom the Software is furnished to do so, subject to
158.16 +// the following conditions:
158.17 +//
158.18 +// The above copyright notice and this permission notice shall be included
158.19 +// in all copies or substantial portions of the Software.
158.20 +//
158.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
158.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
158.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
158.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
158.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
158.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
158.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
158.28 +// </copyright>
158.29 +// <summary>
158.30 +// ANSI text report writer.
158.31 +// </summary>
158.32 +// --------------------------------------------------------------------------------------------------------------------
158.33 +namespace OxyPlot.Reporting
158.34 +{
158.35 + using System;
158.36 + using System.IO;
158.37 +
158.38 + /// <summary>
158.39 + /// ANSI text report writer.
158.40 + /// </summary>
158.41 + /// <remarks>
158.42 + /// This will not write figures/images.
158.43 + /// </remarks>
158.44 + public class TextReportWriter : StreamWriter, IReportWriter
158.45 + {
158.46 + /// <summary>
158.47 + /// The table cell separator.
158.48 + /// </summary>
158.49 + private const string TableCellSeparator = " | ";
158.50 +
158.51 + /// <summary>
158.52 + /// The table row end.
158.53 + /// </summary>
158.54 + private const string TableRowEnd = " |";
158.55 +
158.56 + /// <summary>
158.57 + /// The table row start.
158.58 + /// </summary>
158.59 + private const string TableRowStart = "| ";
158.60 +
158.61 + /// <summary>
158.62 + /// The table counter.
158.63 + /// </summary>
158.64 + private int tableCounter;
158.65 +
158.66 + /// <summary>
158.67 + /// Initializes a new instance of the <see cref="TextReportWriter"/> class.
158.68 + /// </summary>
158.69 + /// <param name="stream">
158.70 + /// The stream.
158.71 + /// </param>
158.72 + public TextReportWriter(Stream stream)
158.73 + : base(stream)
158.74 + {
158.75 + this.MaxLineLength = 60;
158.76 + }
158.77 +
158.78 + /// <summary>
158.79 + /// Gets or sets MaxLineLength.
158.80 + /// </summary>
158.81 + public int MaxLineLength { get; set; }
158.82 +
158.83 + /// <summary>
158.84 + /// The write drawing.
158.85 + /// </summary>
158.86 + /// <param name="d">
158.87 + /// The d.
158.88 + /// </param>
158.89 + public void WriteDrawing(DrawingFigure d)
158.90 + {
158.91 + }
158.92 +
158.93 + /// <summary>
158.94 + /// The write equation.
158.95 + /// </summary>
158.96 + /// <param name="equation">
158.97 + /// The equation.
158.98 + /// </param>
158.99 + public void WriteEquation(Equation equation)
158.100 + {
158.101 + }
158.102 +
158.103 + /// <summary>
158.104 + /// The write header.
158.105 + /// </summary>
158.106 + /// <param name="h">
158.107 + /// The h.
158.108 + /// </param>
158.109 + public void WriteHeader(Header h)
158.110 + {
158.111 + if (h.Text == null)
158.112 + {
158.113 + return;
158.114 + }
158.115 +
158.116 + WriteLine(h);
158.117 + if (h.Level == 1)
158.118 + {
158.119 + this.WriteLine("=".Repeat(h.Text.Length));
158.120 + }
158.121 +
158.122 + this.WriteLine();
158.123 + }
158.124 +
158.125 + /// <summary>
158.126 + /// The write image.
158.127 + /// </summary>
158.128 + /// <param name="i">
158.129 + /// The i.
158.130 + /// </param>
158.131 + public void WriteImage(Image i)
158.132 + {
158.133 + }
158.134 +
158.135 + /// <summary>
158.136 + /// The write paragraph.
158.137 + /// </summary>
158.138 + /// <param name="p">
158.139 + /// The p.
158.140 + /// </param>
158.141 + public void WriteParagraph(Paragraph p)
158.142 + {
158.143 + foreach (string line in p.Text.SplitLines(this.MaxLineLength))
158.144 + {
158.145 + WriteLine(line);
158.146 + }
158.147 +
158.148 + this.WriteLine();
158.149 + }
158.150 +
158.151 + /// <summary>
158.152 + /// The write plot.
158.153 + /// </summary>
158.154 + /// <param name="plot">
158.155 + /// The plot.
158.156 + /// </param>
158.157 + public void WritePlot(PlotFigure plot)
158.158 + {
158.159 + }
158.160 +
158.161 + /// <summary>
158.162 + /// The write report.
158.163 + /// </summary>
158.164 + /// <param name="report">
158.165 + /// The report.
158.166 + /// </param>
158.167 + /// <param name="reportStyle">
158.168 + /// The style.
158.169 + /// </param>
158.170 + public void WriteReport(Report report, ReportStyle reportStyle)
158.171 + {
158.172 + report.Write(this);
158.173 + }
158.174 +
158.175 + /// <summary>
158.176 + /// The write table.
158.177 + /// </summary>
158.178 + /// <param name="t">
158.179 + /// The t.
158.180 + /// </param>
158.181 + public void WriteTable(Table t)
158.182 + {
158.183 + this.tableCounter++;
158.184 + this.WriteLine(string.Format("Table {0}. {1}", this.tableCounter, t.Caption));
158.185 + this.WriteLine();
158.186 + int rows = t.Rows.Count;
158.187 + int cols = t.Columns.Count;
158.188 +
158.189 + var columnWidth = new int[cols];
158.190 + int totalLength = 0;
158.191 + for (int j = 0; j < cols; j++)
158.192 + {
158.193 + columnWidth[j] = 0;
158.194 + foreach (var tr in t.Rows)
158.195 + {
158.196 + TableCell cell = tr.Cells[j];
158.197 + string text = cell.Content;
158.198 + columnWidth[j] = Math.Max(columnWidth[j], text != null ? text.Length : 0);
158.199 + }
158.200 +
158.201 + totalLength += columnWidth[j];
158.202 + }
158.203 +
158.204 + // WriteLine("-".Repeat(totalLength));
158.205 + foreach (var tr in t.Rows)
158.206 + {
158.207 + for (int j = 0; j < cols; j++)
158.208 + {
158.209 + TableCell cell = tr.Cells[j];
158.210 + string text = cell.Content;
158.211 + this.Write(GetCellText(j, cols, PadString(text, t.Columns[j].Alignment, columnWidth[j])));
158.212 + }
158.213 +
158.214 + this.WriteLine();
158.215 + }
158.216 +
158.217 + this.WriteLine();
158.218 + }
158.219 +
158.220 + /// <summary>
158.221 + /// The get cell text.
158.222 + /// </summary>
158.223 + /// <param name="i">
158.224 + /// The i.
158.225 + /// </param>
158.226 + /// <param name="count">
158.227 + /// The count.
158.228 + /// </param>
158.229 + /// <param name="p">
158.230 + /// The p.
158.231 + /// </param>
158.232 + /// <returns>
158.233 + /// The get cell text.
158.234 + /// </returns>
158.235 + private static string GetCellText(int i, int count, string p)
158.236 + {
158.237 + if (i == 0)
158.238 + {
158.239 + p = TableRowStart + p;
158.240 + }
158.241 +
158.242 + if (i + 1 < count)
158.243 + {
158.244 + p += TableCellSeparator;
158.245 + }
158.246 +
158.247 + if (i == count - 1)
158.248 + {
158.249 + p += TableRowEnd;
158.250 + }
158.251 +
158.252 + return p;
158.253 + }
158.254 +
158.255 + /// <summary>
158.256 + /// The pad string.
158.257 + /// </summary>
158.258 + /// <param name="text">
158.259 + /// The text.
158.260 + /// </param>
158.261 + /// <param name="alignment">
158.262 + /// The alignment.
158.263 + /// </param>
158.264 + /// <param name="width">
158.265 + /// The width.
158.266 + /// </param>
158.267 + /// <returns>
158.268 + /// The pad string.
158.269 + /// </returns>
158.270 + private static string PadString(string text, Alignment alignment, int width)
158.271 + {
158.272 + if (text == null)
158.273 + {
158.274 + return string.Empty.PadLeft(width);
158.275 + }
158.276 +
158.277 + switch (alignment)
158.278 + {
158.279 + case Alignment.Left:
158.280 + return text.PadRight(width);
158.281 + case Alignment.Right:
158.282 + return text.PadLeft(width);
158.283 + case Alignment.Center:
158.284 + text = text.PadRight((text.Length + width) / 2);
158.285 + return text.PadLeft(width);
158.286 + }
158.287 +
158.288 + return null;
158.289 + }
158.290 +
158.291 + }
158.292 +}
158.293 \ No newline at end of file
159.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
159.2 +++ b/External/OxyPlot/OxyPlot/Reporting/ReportWriters/WikiReportWriter.cs Sat Jun 08 16:53:22 2013 +0000
159.3 @@ -0,0 +1,308 @@
159.4 +// --------------------------------------------------------------------------------------------------------------------
159.5 +// <copyright file="WikiReportWriter.cs" company="OxyPlot">
159.6 +// The MIT License (MIT)
159.7 +//
159.8 +// Copyright (c) 2012 Oystein Bjorke
159.9 +//
159.10 +// Permission is hereby granted, free of charge, to any person obtaining a
159.11 +// copy of this software and associated documentation files (the
159.12 +// "Software"), to deal in the Software without restriction, including
159.13 +// without limitation the rights to use, copy, modify, merge, publish,
159.14 +// distribute, sublicense, and/or sell copies of the Software, and to
159.15 +// permit persons to whom the Software is furnished to do so, subject to
159.16 +// the following conditions:
159.17 +//
159.18 +// The above copyright notice and this permission notice shall be included
159.19 +// in all copies or substantial portions of the Software.
159.20 +//
159.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
159.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
159.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
159.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
159.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
159.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
159.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
159.28 +// </copyright>
159.29 +// <summary>
159.30 +// Wiki formatting report writer.
159.31 +// </summary>
159.32 +// --------------------------------------------------------------------------------------------------------------------
159.33 +namespace OxyPlot.Reporting
159.34 +{
159.35 + using System;
159.36 + using System.IO;
159.37 +
159.38 + /// <summary>
159.39 + /// Wiki formatting report writer.
159.40 + /// </summary>
159.41 + /// <remarks>
159.42 + /// This will not write figures/images.
159.43 + /// </remarks>
159.44 + public class WikiReportWriter : StreamWriter, IReportWriter
159.45 + {
159.46 + /// <summary>
159.47 + /// The table cell separator.
159.48 + /// </summary>
159.49 + private const string TableCellSeparator = " | ";
159.50 +
159.51 + /// <summary>
159.52 + /// The table header cell separator.
159.53 + /// </summary>
159.54 + private const string TableHeaderCellSeparator = " || ";
159.55 +
159.56 + /// <summary>
159.57 + /// The table header row end.
159.58 + /// </summary>
159.59 + private const string TableHeaderRowEnd = " ||";
159.60 +
159.61 + /// <summary>
159.62 + /// The table header row start.
159.63 + /// </summary>
159.64 + private const string TableHeaderRowStart = "|| ";
159.65 +
159.66 + /// <summary>
159.67 + /// The table row end.
159.68 + /// </summary>
159.69 + private const string TableRowEnd = " |";
159.70 +
159.71 + /// <summary>
159.72 + /// The table row start.
159.73 + /// </summary>
159.74 + private const string TableRowStart = "| ";
159.75 +
159.76 + /// <summary>
159.77 + /// The table counter.
159.78 + /// </summary>
159.79 + private int tableCounter;
159.80 +
159.81 + /// <summary>
159.82 + /// Initializes a new instance of the <see cref="WikiReportWriter"/> class.
159.83 + /// </summary>
159.84 + /// <param name="s">
159.85 + /// The s.
159.86 + /// </param>
159.87 + public WikiReportWriter(Stream s)
159.88 + : base(s)
159.89 + {
159.90 + this.MaxLineLength = 60;
159.91 + }
159.92 +
159.93 + /// <summary>
159.94 + /// Gets or sets MaxLineLength.
159.95 + /// </summary>
159.96 + public int MaxLineLength { get; set; }
159.97 +
159.98 + /// <summary>
159.99 + /// The write drawing.
159.100 + /// </summary>
159.101 + /// <param name="d">
159.102 + /// The d.
159.103 + /// </param>
159.104 + public void WriteDrawing(DrawingFigure d)
159.105 + {
159.106 + }
159.107 +
159.108 + /// <summary>
159.109 + /// The write equation.
159.110 + /// </summary>
159.111 + /// <param name="equation">
159.112 + /// The equation.
159.113 + /// </param>
159.114 + public void WriteEquation(Equation equation)
159.115 + {
159.116 + }
159.117 +
159.118 + /// <summary>
159.119 + /// The write header.
159.120 + /// </summary>
159.121 + /// <param name="h">
159.122 + /// The h.
159.123 + /// </param>
159.124 + public void WriteHeader(Header h)
159.125 + {
159.126 + if (h.Text == null)
159.127 + {
159.128 + return;
159.129 + }
159.130 +
159.131 + string prefix = string.Empty;
159.132 + for (int i = 0; i < h.Level; i++)
159.133 + {
159.134 + prefix += "!";
159.135 + }
159.136 +
159.137 + this.WriteLine(prefix + " " + h.Text);
159.138 + }
159.139 +
159.140 + /// <summary>
159.141 + /// The write image.
159.142 + /// </summary>
159.143 + /// <param name="i">
159.144 + /// The i.
159.145 + /// </param>
159.146 + public void WriteImage(Image i)
159.147 + {
159.148 + }
159.149 +
159.150 + /// <summary>
159.151 + /// The write paragraph.
159.152 + /// </summary>
159.153 + /// <param name="p">
159.154 + /// The p.
159.155 + /// </param>
159.156 + public void WriteParagraph(Paragraph p)
159.157 + {
159.158 + foreach (string line in p.Text.SplitLines(this.MaxLineLength))
159.159 + {
159.160 + WriteLine(line);
159.161 + }
159.162 +
159.163 + this.WriteLine();
159.164 + }
159.165 +
159.166 + /// <summary>
159.167 + /// The write plot.
159.168 + /// </summary>
159.169 + /// <param name="plot">
159.170 + /// The plot.
159.171 + /// </param>
159.172 + public void WritePlot(PlotFigure plot)
159.173 + {
159.174 + }
159.175 +
159.176 + /// <summary>
159.177 + /// The write report.
159.178 + /// </summary>
159.179 + /// <param name="report">
159.180 + /// The report.
159.181 + /// </param>
159.182 + /// <param name="reportStyle">
159.183 + /// The style.
159.184 + /// </param>
159.185 + public void WriteReport(Report report, ReportStyle reportStyle)
159.186 + {
159.187 + report.Write(this);
159.188 + }
159.189 +
159.190 + /// <summary>
159.191 + /// The write table.
159.192 + /// </summary>
159.193 + /// <param name="t">
159.194 + /// The t.
159.195 + /// </param>
159.196 + public void WriteTable(Table t)
159.197 + {
159.198 + this.tableCounter++;
159.199 + this.WriteLine(string.Format("Table {0}. {1}", this.tableCounter, t.Caption));
159.200 + this.WriteLine();
159.201 + int rows = t.Rows.Count;
159.202 + int cols = t.Columns.Count;
159.203 +
159.204 + var columnWidth = new int[cols];
159.205 + int totalLength = 0;
159.206 + for (int j = 0; j < cols; j++)
159.207 + {
159.208 + columnWidth[j] = 0;
159.209 + foreach (var tr in t.Rows)
159.210 + {
159.211 + TableCell cell = tr.Cells[j];
159.212 + string text = cell.Content;
159.213 + columnWidth[j] = Math.Max(columnWidth[j], text != null ? text.Length : 0);
159.214 + }
159.215 +
159.216 + totalLength += columnWidth[j];
159.217 + }
159.218 +
159.219 + // WriteLine("-".Repeat(totalLength));
159.220 + foreach (var tr in t.Rows)
159.221 + {
159.222 + for (int j = 0; j < cols; j++)
159.223 + {
159.224 + TableCell cell = tr.Cells[j];
159.225 + string text = cell.Content;
159.226 + bool isHeader = tr.IsHeader || t.Columns[j].IsHeader;
159.227 + this.Write(GetCellText(j, cols, PadString(text, t.Columns[j].Alignment, columnWidth[j]), isHeader));
159.228 + }
159.229 +
159.230 + this.WriteLine();
159.231 + }
159.232 +
159.233 + this.WriteLine();
159.234 + }
159.235 +
159.236 + /// <summary>
159.237 + /// The get cell text.
159.238 + /// </summary>
159.239 + /// <param name="i">
159.240 + /// The i.
159.241 + /// </param>
159.242 + /// <param name="count">
159.243 + /// The count.
159.244 + /// </param>
159.245 + /// <param name="p">
159.246 + /// The p.
159.247 + /// </param>
159.248 + /// <param name="isHeader">
159.249 + /// The is header.
159.250 + /// </param>
159.251 + /// <returns>
159.252 + /// The get cell text.
159.253 + /// </returns>
159.254 + private static string GetCellText(int i, int count, string p, bool isHeader)
159.255 + {
159.256 + if (i == 0)
159.257 + {
159.258 + p = isHeader ? TableHeaderRowStart : TableRowStart + p;
159.259 + }
159.260 +
159.261 + if (i + 1 < count)
159.262 + {
159.263 + p += isHeader ? TableHeaderCellSeparator : TableCellSeparator;
159.264 + }
159.265 +
159.266 + if (i == count - 1)
159.267 + {
159.268 + p += isHeader ? TableHeaderRowEnd : TableRowEnd;
159.269 + }
159.270 +
159.271 + return p;
159.272 + }
159.273 +
159.274 + /// <summary>
159.275 + /// The pad string.
159.276 + /// </summary>
159.277 + /// <param name="text">
159.278 + /// The text.
159.279 + /// </param>
159.280 + /// <param name="alignment">
159.281 + /// The alignment.
159.282 + /// </param>
159.283 + /// <param name="width">
159.284 + /// The width.
159.285 + /// </param>
159.286 + /// <returns>
159.287 + /// The pad string.
159.288 + /// </returns>
159.289 + private static string PadString(string text, Alignment alignment, int width)
159.290 + {
159.291 + if (text == null)
159.292 + {
159.293 + return string.Empty.PadLeft(width);
159.294 + }
159.295 +
159.296 + switch (alignment)
159.297 + {
159.298 + case Alignment.Left:
159.299 + return text.PadRight(width);
159.300 + case Alignment.Right:
159.301 + return text.PadLeft(width);
159.302 + case Alignment.Center:
159.303 + text = text.PadRight((text.Length + width) / 2);
159.304 + return text.PadLeft(width);
159.305 + }
159.306 +
159.307 + return null;
159.308 + }
159.309 +
159.310 + }
159.311 +}
159.312 \ No newline at end of file
160.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
160.2 +++ b/External/OxyPlot/OxyPlot/Series/AreaSeries.cs Sat Jun 08 16:53:22 2013 +0000
160.3 @@ -0,0 +1,295 @@
160.4 +// --------------------------------------------------------------------------------------------------------------------
160.5 +// <copyright file="AreaSeries.cs" company="OxyPlot">
160.6 +// The MIT License (MIT)
160.7 +//
160.8 +// Copyright (c) 2012 Oystein Bjorke
160.9 +//
160.10 +// Permission is hereby granted, free of charge, to any person obtaining a
160.11 +// copy of this software and associated documentation files (the
160.12 +// "Software"), to deal in the Software without restriction, including
160.13 +// without limitation the rights to use, copy, modify, merge, publish,
160.14 +// distribute, sublicense, and/or sell copies of the Software, and to
160.15 +// permit persons to whom the Software is furnished to do so, subject to
160.16 +// the following conditions:
160.17 +//
160.18 +// The above copyright notice and this permission notice shall be included
160.19 +// in all copies or substantial portions of the Software.
160.20 +//
160.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
160.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
160.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
160.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
160.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
160.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
160.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
160.28 +// </copyright>
160.29 +// <summary>
160.30 +// Represents an area series that fills the polygon defined by one or two sets of points.
160.31 +// </summary>
160.32 +// --------------------------------------------------------------------------------------------------------------------
160.33 +namespace OxyPlot.Series
160.34 +{
160.35 + using System;
160.36 + using System.Collections.Generic;
160.37 +
160.38 + /// <summary>
160.39 + /// Represents an area series that fills the polygon defined by two sets of points or one set of points and a constant.
160.40 + /// </summary>
160.41 + public class AreaSeries : LineSeries
160.42 + {
160.43 + /// <summary>
160.44 + /// The second list of points.
160.45 + /// </summary>
160.46 + private readonly List<IDataPoint> points2 = new List<IDataPoint>();
160.47 +
160.48 + /// <summary>
160.49 + /// Initializes a new instance of the <see cref = "AreaSeries" /> class.
160.50 + /// </summary>
160.51 + public AreaSeries()
160.52 + {
160.53 + this.Reverse2 = true;
160.54 + }
160.55 +
160.56 + /// <summary>
160.57 + /// Gets or sets a constant value for the area definition.
160.58 + /// This is used if DataFieldBase and BaselineValues are null.
160.59 + /// </summary>
160.60 + /// <value>The baseline.</value>
160.61 + public double ConstantY2 { get; set; }
160.62 +
160.63 + /// <summary>
160.64 + /// Gets or sets the second X data field.
160.65 + /// </summary>
160.66 + public string DataFieldX2 { get; set; }
160.67 +
160.68 + /// <summary>
160.69 + /// Gets or sets the second Y data field.
160.70 + /// </summary>
160.71 + public string DataFieldY2 { get; set; }
160.72 +
160.73 + /// <summary>
160.74 + /// Gets or sets the area fill color.
160.75 + /// </summary>
160.76 + /// <value>The fill.</value>
160.77 + public OxyColor Fill { get; set; }
160.78 +
160.79 + /// <summary>
160.80 + /// Gets the second list of points.
160.81 + /// </summary>
160.82 + /// <value>The second list of points.</value>
160.83 + public List<IDataPoint> Points2
160.84 + {
160.85 + get
160.86 + {
160.87 + return this.points2;
160.88 + }
160.89 + }
160.90 +
160.91 + /// <summary>
160.92 + /// Gets or sets a value indicating whether the second
160.93 + /// data collection should be reversed.
160.94 + /// The first dataset is not reversed, and normally
160.95 + /// the second dataset should be reversed to get a
160.96 + /// closed polygon.
160.97 + /// </summary>
160.98 + public bool Reverse2 { get; set; }
160.99 +
160.100 + /// <summary>
160.101 + /// Gets the nearest point.
160.102 + /// </summary>
160.103 + /// <param name="point">The point.</param>
160.104 + /// <param name="interpolate">interpolate if set to <c>true</c> .</param>
160.105 + /// <returns>A TrackerHitResult for the current hit.</returns>
160.106 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
160.107 + {
160.108 + if (interpolate)
160.109 + {
160.110 + var r1 = this.GetNearestInterpolatedPointInternal(this.Points, point);
160.111 + if (r1 != null)
160.112 + {
160.113 + return r1;
160.114 + }
160.115 +
160.116 + var r2 = this.GetNearestInterpolatedPointInternal(this.points2, point);
160.117 + if (r2 != null)
160.118 + {
160.119 + return r2;
160.120 + }
160.121 + }
160.122 + else
160.123 + {
160.124 + var result1 = this.GetNearestPointInternal(this.Points, point);
160.125 + var result2 = this.GetNearestPointInternal(this.points2, point);
160.126 +
160.127 + if (result1 != null && result2 != null)
160.128 + {
160.129 + double dist1 = result1.Position.DistanceTo(point);
160.130 + double dist2 = result2.Position.DistanceTo(point);
160.131 + return dist1 < dist2 ? result1 : result2;
160.132 + }
160.133 +
160.134 + if (result1 != null)
160.135 + {
160.136 + return result1;
160.137 + }
160.138 +
160.139 + if (result2 != null)
160.140 + {
160.141 + return result2;
160.142 + }
160.143 + }
160.144 +
160.145 + return null;
160.146 + }
160.147 +
160.148 + /// <summary>
160.149 + /// Renders the series on the specified rendering context.
160.150 + /// </summary>
160.151 + /// <param name="rc">The rendering context.</param>
160.152 + /// <param name="model">The owner plot model.</param>
160.153 + public override void Render(IRenderContext rc, PlotModel model)
160.154 + {
160.155 + if (this.Points.Count == 0)
160.156 + {
160.157 + return;
160.158 + }
160.159 +
160.160 + base.VerifyAxes();
160.161 +
160.162 + double minDistSquared = this.MinimumSegmentLength * this.MinimumSegmentLength;
160.163 +
160.164 + var clippingRect = this.GetClippingRect();
160.165 +
160.166 + // Transform all points to screen coordinates
160.167 + var points = this.Points;
160.168 + int n0 = points.Count;
160.169 + IList<ScreenPoint> pts0 = new ScreenPoint[n0];
160.170 + for (int i = 0; i < n0; i++)
160.171 + {
160.172 + pts0[i] = this.XAxis.Transform(points[i].X, points[i].Y, this.YAxis);
160.173 + }
160.174 +
160.175 + int n1 = this.points2.Count;
160.176 + IList<ScreenPoint> pts1 = new ScreenPoint[n1];
160.177 + for (int i = 0; i < n1; i++)
160.178 + {
160.179 + int j = this.Reverse2 ? n1 - 1 - i : i;
160.180 + pts1[j] = this.XAxis.Transform(this.points2[i].X, this.points2[i].Y, this.YAxis);
160.181 + }
160.182 +
160.183 + if (this.Smooth)
160.184 + {
160.185 + var rpts0 = ScreenPointHelper.ResamplePoints(pts0, this.MinimumSegmentLength);
160.186 + var rpts1 = ScreenPointHelper.ResamplePoints(pts1, this.MinimumSegmentLength);
160.187 +
160.188 + pts0 = CanonicalSplineHelper.CreateSpline(rpts0, 0.5, null, false, 0.25);
160.189 + pts1 = CanonicalSplineHelper.CreateSpline(rpts1, 0.5, null, false, 0.25);
160.190 + }
160.191 +
160.192 + // draw the clipped lines
160.193 + rc.DrawClippedLine(
160.194 + pts0,
160.195 + clippingRect,
160.196 + minDistSquared,
160.197 + this.GetSelectableColor(this.ActualColor),
160.198 + this.StrokeThickness,
160.199 + this.ActualLineStyle,
160.200 + this.LineJoin,
160.201 + false);
160.202 + rc.DrawClippedLine(
160.203 + pts1,
160.204 + clippingRect,
160.205 + minDistSquared,
160.206 + this.GetSelectableColor(this.ActualColor),
160.207 + this.StrokeThickness,
160.208 + this.ActualLineStyle,
160.209 + this.LineJoin,
160.210 + false);
160.211 +
160.212 + // combine the two lines and draw the clipped area
160.213 + var pts = new List<ScreenPoint>();
160.214 + pts.AddRange(pts1);
160.215 + pts.AddRange(pts0);
160.216 +
160.217 + // pts = SutherlandHodgmanClipping.ClipPolygon(clippingRect, pts);
160.218 + rc.DrawClippedPolygon(pts, clippingRect, minDistSquared, this.GetSelectableFillColor(this.Fill), null);
160.219 +
160.220 + // draw the markers on top
160.221 + rc.DrawMarkers(
160.222 + pts0,
160.223 + clippingRect,
160.224 + this.MarkerType,
160.225 + null,
160.226 + new[] { this.MarkerSize },
160.227 + this.MarkerFill,
160.228 + this.MarkerStroke,
160.229 + this.MarkerStrokeThickness,
160.230 + 1);
160.231 + rc.DrawMarkers(
160.232 + pts1,
160.233 + clippingRect,
160.234 + this.MarkerType,
160.235 + null,
160.236 + new[] { this.MarkerSize },
160.237 + this.MarkerFill,
160.238 + this.MarkerStroke,
160.239 + this.MarkerStrokeThickness,
160.240 + 1);
160.241 + }
160.242 +
160.243 + /// <summary>
160.244 + /// Renders the legend symbol for the line series on the
160.245 + /// specified rendering context.
160.246 + /// </summary>
160.247 + /// <param name="rc">
160.248 + /// The rendering context.
160.249 + /// </param>
160.250 + /// <param name="legendBox">
160.251 + /// The bounding rectangle of the legend box.
160.252 + /// </param>
160.253 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
160.254 + {
160.255 + double y0 = (legendBox.Top * 0.2) + (legendBox.Bottom * 0.8);
160.256 + double y1 = (legendBox.Top * 0.4) + (legendBox.Bottom * 0.6);
160.257 + double y2 = (legendBox.Top * 0.8) + (legendBox.Bottom * 0.2);
160.258 +
160.259 + var pts0 = new[] { new ScreenPoint(legendBox.Left, y0), new ScreenPoint(legendBox.Right, y0) };
160.260 + var pts1 = new[] { new ScreenPoint(legendBox.Right, y2), new ScreenPoint(legendBox.Left, y1) };
160.261 + var pts = new List<ScreenPoint>();
160.262 + pts.AddRange(pts0);
160.263 + pts.AddRange(pts1);
160.264 + var color = this.GetSelectableColor(this.ActualColor);
160.265 + rc.DrawLine(pts0, color, this.StrokeThickness, LineStyleHelper.GetDashArray(this.ActualLineStyle));
160.266 + rc.DrawLine(pts1, color, this.StrokeThickness, LineStyleHelper.GetDashArray(this.ActualLineStyle));
160.267 + rc.DrawPolygon(pts, this.GetSelectableFillColor(this.Fill), null);
160.268 + }
160.269 +
160.270 + /// <summary>
160.271 + /// The update data.
160.272 + /// </summary>
160.273 + protected internal override void UpdateData()
160.274 + {
160.275 + base.UpdateData();
160.276 +
160.277 + if (this.ItemsSource == null)
160.278 + {
160.279 + return;
160.280 + }
160.281 +
160.282 + this.points2.Clear();
160.283 +
160.284 + // Using reflection on DataFieldX2 and DataFieldY2
160.285 + this.AddDataPoints(this.points2, this.ItemsSource, this.DataFieldX2, this.DataFieldY2);
160.286 + }
160.287 +
160.288 + /// <summary>
160.289 + /// The update max min.
160.290 + /// </summary>
160.291 + protected internal override void UpdateMaxMin()
160.292 + {
160.293 + base.UpdateMaxMin();
160.294 + this.InternalUpdateMaxMin(this.points2);
160.295 + }
160.296 +
160.297 + }
160.298 +}
160.299 \ No newline at end of file
161.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
161.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/BarItem.cs Sat Jun 08 16:53:22 2013 +0000
161.3 @@ -0,0 +1,64 @@
161.4 +// --------------------------------------------------------------------------------------------------------------------
161.5 +// <copyright file="BarItem.cs" company="OxyPlot">
161.6 +// The MIT License (MIT)
161.7 +//
161.8 +// Copyright (c) 2012 Oystein Bjorke
161.9 +//
161.10 +// Permission is hereby granted, free of charge, to any person obtaining a
161.11 +// copy of this software and associated documentation files (the
161.12 +// "Software"), to deal in the Software without restriction, including
161.13 +// without limitation the rights to use, copy, modify, merge, publish,
161.14 +// distribute, sublicense, and/or sell copies of the Software, and to
161.15 +// permit persons to whom the Software is furnished to do so, subject to
161.16 +// the following conditions:
161.17 +//
161.18 +// The above copyright notice and this permission notice shall be included
161.19 +// in all copies or substantial portions of the Software.
161.20 +//
161.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
161.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
161.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
161.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
161.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
161.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
161.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
161.28 +// </copyright>
161.29 +// <summary>
161.30 +// Represents an item used in the BarSeries.
161.31 +// </summary>
161.32 +// --------------------------------------------------------------------------------------------------------------------
161.33 +namespace OxyPlot.Series
161.34 +{
161.35 + /// <summary>
161.36 + /// Represents an item used in the BarSeries.
161.37 + /// </summary>
161.38 + public class BarItem : BarItemBase
161.39 + {
161.40 + /// <summary>
161.41 + /// Initializes a new instance of the <see cref="BarItem"/> class.
161.42 + /// </summary>
161.43 + public BarItem()
161.44 + {
161.45 + }
161.46 +
161.47 + /// <summary>
161.48 + /// Initializes a new instance of the <see cref="BarItem"/> class.
161.49 + /// </summary>
161.50 + /// <param name="value">
161.51 + /// The value.
161.52 + /// </param>
161.53 + /// <param name="categoryIndex">
161.54 + /// Index of the category.
161.55 + /// </param>
161.56 + /// <param name="color">
161.57 + /// The color.
161.58 + /// </param>
161.59 + public BarItem(double value, int categoryIndex = -1, OxyColor color = null)
161.60 + {
161.61 + this.Value = value;
161.62 + this.CategoryIndex = categoryIndex;
161.63 + this.Color = color;
161.64 + }
161.65 +
161.66 + }
161.67 +}
161.68 \ No newline at end of file
162.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
162.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/BarItemBase.cs Sat Jun 08 16:53:22 2013 +0000
162.3 @@ -0,0 +1,83 @@
162.4 +// --------------------------------------------------------------------------------------------------------------------
162.5 +// <copyright file="BarItemBase.cs" company="OxyPlot">
162.6 +// The MIT License (MIT)
162.7 +//
162.8 +// Copyright (c) 2012 Oystein Bjorke
162.9 +//
162.10 +// Permission is hereby granted, free of charge, to any person obtaining a
162.11 +// copy of this software and associated documentation files (the
162.12 +// "Software"), to deal in the Software without restriction, including
162.13 +// without limitation the rights to use, copy, modify, merge, publish,
162.14 +// distribute, sublicense, and/or sell copies of the Software, and to
162.15 +// permit persons to whom the Software is furnished to do so, subject to
162.16 +// the following conditions:
162.17 +//
162.18 +// The above copyright notice and this permission notice shall be included
162.19 +// in all copies or substantial portions of the Software.
162.20 +//
162.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
162.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
162.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
162.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
162.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
162.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
162.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
162.28 +// </copyright>
162.29 +// <summary>
162.30 +// Represents an item used in the BarSeriesBase.
162.31 +// </summary>
162.32 +// --------------------------------------------------------------------------------------------------------------------
162.33 +namespace OxyPlot.Series
162.34 +{
162.35 + /// <summary>
162.36 + /// Represents an item used in the BarSeriesBase.
162.37 + /// </summary>
162.38 + public abstract class BarItemBase : CategorizedItem, ICodeGenerating
162.39 + {
162.40 + /// <summary>
162.41 + /// Initializes a new instance of the <see cref="BarItemBase"/> class. Initializes a new instance of the <see cref="BarItem"/> class.
162.42 + /// </summary>
162.43 + protected BarItemBase()
162.44 + {
162.45 + // Label = null;
162.46 + this.Value = double.NaN;
162.47 + this.Color = null;
162.48 + }
162.49 +
162.50 + /// <summary>
162.51 + /// Gets or sets the color of the item.
162.52 + /// </summary>
162.53 + /// <remarks>
162.54 + /// If the color is not specified (default), the color of the series will be used.
162.55 + /// </remarks>
162.56 + public OxyColor Color { get; set; }
162.57 +
162.58 + /// <summary>
162.59 + /// Gets or sets the value of the item.
162.60 + /// </summary>
162.61 + public double Value { get; set; }
162.62 +
162.63 + /// <summary>
162.64 + /// Returns c# code that generates this instance.
162.65 + /// </summary>
162.66 + /// <returns>
162.67 + /// C# code.
162.68 + /// </returns>
162.69 + public virtual string ToCode()
162.70 + {
162.71 + if (this.Color != null)
162.72 + {
162.73 + return CodeGenerator.FormatConstructor(
162.74 + this.GetType(), "{0},{1},{2}", this.Value, this.CategoryIndex, this.Color.ToCode());
162.75 + }
162.76 +
162.77 + if (this.CategoryIndex != -1)
162.78 + {
162.79 + return CodeGenerator.FormatConstructor(this.GetType(), "{0},{1}", this.Value, this.CategoryIndex);
162.80 + }
162.81 +
162.82 + return CodeGenerator.FormatConstructor(this.GetType(), "{0}", this.Value);
162.83 + }
162.84 +
162.85 + }
162.86 +}
162.87 \ No newline at end of file
163.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
163.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/BarSeries.cs Sat Jun 08 16:53:22 2013 +0000
163.3 @@ -0,0 +1,198 @@
163.4 +// --------------------------------------------------------------------------------------------------------------------
163.5 +// <copyright file="BarSeries.cs" company="OxyPlot">
163.6 +// The MIT License (MIT)
163.7 +//
163.8 +// Copyright (c) 2012 Oystein Bjorke
163.9 +//
163.10 +// Permission is hereby granted, free of charge, to any person obtaining a
163.11 +// copy of this software and associated documentation files (the
163.12 +// "Software"), to deal in the Software without restriction, including
163.13 +// without limitation the rights to use, copy, modify, merge, publish,
163.14 +// distribute, sublicense, and/or sell copies of the Software, and to
163.15 +// permit persons to whom the Software is furnished to do so, subject to
163.16 +// the following conditions:
163.17 +//
163.18 +// The above copyright notice and this permission notice shall be included
163.19 +// in all copies or substantial portions of the Software.
163.20 +//
163.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
163.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
163.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
163.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
163.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
163.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
163.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
163.28 +// </copyright>
163.29 +// <summary>
163.30 +// Represents a series for clustered or stacked bar charts.
163.31 +// </summary>
163.32 +// --------------------------------------------------------------------------------------------------------------------
163.33 +namespace OxyPlot.Series
163.34 +{
163.35 + using System;
163.36 +
163.37 + using OxyPlot.Axes;
163.38 +
163.39 + /// <summary>
163.40 + /// Represents a series for clustered or stacked bar charts.
163.41 + /// </summary>
163.42 + public class BarSeries : BarSeriesBase<BarItem>
163.43 + {
163.44 + /// <summary>
163.45 + /// Initializes a new instance of the <see cref="BarSeries"/> class.
163.46 + /// </summary>
163.47 + public BarSeries()
163.48 + {
163.49 + this.BarWidth = 1;
163.50 + }
163.51 +
163.52 + /// <summary>
163.53 + /// Gets or sets the width (height) of the bars.
163.54 + /// </summary>
163.55 + /// <value>
163.56 + /// The width of the bars.
163.57 + /// </value>
163.58 + public double BarWidth { get; set; }
163.59 +
163.60 + /// <summary>
163.61 + /// Gets or sets the width of the columns/bars (as a fraction of the available space).
163.62 + /// </summary>
163.63 + /// <returns>
163.64 + /// The fractional width.
163.65 + /// </returns>
163.66 + /// <value>
163.67 + /// The width of the bars.
163.68 + /// </value>
163.69 + /// <remarks>
163.70 + /// The available space will be determined by the GapWidth of the CategoryAxis used by this series.
163.71 + /// </remarks>
163.72 + internal override double GetBarWidth()
163.73 + {
163.74 + return this.BarWidth;
163.75 + }
163.76 +
163.77 + /// <summary>
163.78 + /// Gets the actual width/height of the items of this series.
163.79 + /// </summary>
163.80 + /// <returns>
163.81 + /// The width or height.
163.82 + /// </returns>
163.83 + /// <remarks>
163.84 + /// The actual width is also influenced by the GapWidth of the CategoryAxis used by this series.
163.85 + /// </remarks>
163.86 + protected override double GetActualBarWidth()
163.87 + {
163.88 + var categoryAxis = this.GetCategoryAxis();
163.89 + return this.BarWidth / (1 + categoryAxis.GapWidth) / categoryAxis.MaxWidth;
163.90 + }
163.91 +
163.92 + /// <summary>
163.93 + /// Gets the category axis.
163.94 + /// </summary>
163.95 + /// <returns>
163.96 + /// The category axis.
163.97 + /// </returns>
163.98 + protected override CategoryAxis GetCategoryAxis()
163.99 + {
163.100 + if (!(this.YAxis is CategoryAxis))
163.101 + {
163.102 + throw new Exception(
163.103 + "A BarSeries requires a CategoryAxis on the y-axis. Use a ColumnSeries if you want vertical bars.");
163.104 + }
163.105 +
163.106 + return this.YAxis as CategoryAxis;
163.107 + }
163.108 +
163.109 + /// <summary>
163.110 + /// Gets the rectangle for the specified values.
163.111 + /// </summary>
163.112 + /// <param name="baseValue">
163.113 + /// The base value of the bar
163.114 + /// </param>
163.115 + /// <param name="topValue">
163.116 + /// The top value of the bar
163.117 + /// </param>
163.118 + /// <param name="beginValue">
163.119 + /// The begin value of the bar
163.120 + /// </param>
163.121 + /// <param name="endValue">
163.122 + /// The end value of the bar
163.123 + /// </param>
163.124 + /// <returns>
163.125 + /// The rectangle.
163.126 + /// </returns>
163.127 + protected override OxyRect GetRectangle(double baseValue, double topValue, double beginValue, double endValue)
163.128 + {
163.129 + return OxyRect.Create(this.Transform(baseValue, beginValue), this.Transform(topValue, endValue));
163.130 + }
163.131 +
163.132 + /// <summary>
163.133 + /// Gets the value axis.
163.134 + /// </summary>
163.135 + /// <returns>
163.136 + /// The value axis.
163.137 + /// </returns>
163.138 + protected override Axis GetValueAxis()
163.139 + {
163.140 + return this.XAxis;
163.141 + }
163.142 +
163.143 + /// <summary>
163.144 + /// Draws the label.
163.145 + /// </summary>
163.146 + /// <param name="rc">
163.147 + /// The render context.
163.148 + /// </param>
163.149 + /// <param name="clippingRect">
163.150 + /// The clipping rect.
163.151 + /// </param>
163.152 + /// <param name="rect">
163.153 + /// The rect.
163.154 + /// </param>
163.155 + /// <param name="value">
163.156 + /// The value.
163.157 + /// </param>
163.158 + /// <param name="i">
163.159 + /// The i.
163.160 + /// </param>
163.161 + protected override void RenderLabel(IRenderContext rc, OxyRect clippingRect, OxyRect rect, double value, int i)
163.162 + {
163.163 + var s = StringHelper.Format(
163.164 + this.ActualCulture, this.LabelFormatString, this.GetItem(this.ValidItemsIndexInversion[i]), value);
163.165 + HorizontalAlignment ha;
163.166 + ScreenPoint pt;
163.167 + switch (this.LabelPlacement)
163.168 + {
163.169 + case LabelPlacement.Inside:
163.170 + pt = new ScreenPoint(rect.Right - this.LabelMargin, (rect.Top + rect.Bottom) / 2);
163.171 + ha = HorizontalAlignment.Right;
163.172 + break;
163.173 + case LabelPlacement.Middle:
163.174 + pt = new ScreenPoint((rect.Left + rect.Right) / 2, (rect.Top + rect.Bottom) / 2);
163.175 + ha = HorizontalAlignment.Center;
163.176 + break;
163.177 + case LabelPlacement.Base:
163.178 + pt = new ScreenPoint(rect.Left + this.LabelMargin, (rect.Top + rect.Bottom) / 2);
163.179 + ha = HorizontalAlignment.Left;
163.180 + break;
163.181 + default: // Outside
163.182 + pt = new ScreenPoint(rect.Right + this.LabelMargin, (rect.Top + rect.Bottom) / 2);
163.183 + ha = HorizontalAlignment.Left;
163.184 + break;
163.185 + }
163.186 +
163.187 + rc.DrawClippedText(
163.188 + clippingRect,
163.189 + pt,
163.190 + s,
163.191 + this.ActualTextColor,
163.192 + this.ActualFont,
163.193 + this.ActualFontSize,
163.194 + this.ActualFontWeight,
163.195 + 0,
163.196 + ha,
163.197 + VerticalAlignment.Middle);
163.198 + }
163.199 +
163.200 + }
163.201 +}
163.202 \ No newline at end of file
164.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
164.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/BarSeriesBase.cs Sat Jun 08 16:53:22 2013 +0000
164.3 @@ -0,0 +1,603 @@
164.4 +// --------------------------------------------------------------------------------------------------------------------
164.5 +// <copyright file="BarSeriesBase.cs" company="OxyPlot">
164.6 +// The MIT License (MIT)
164.7 +//
164.8 +// Copyright (c) 2012 Oystein Bjorke
164.9 +//
164.10 +// Permission is hereby granted, free of charge, to any person obtaining a
164.11 +// copy of this software and associated documentation files (the
164.12 +// "Software"), to deal in the Software without restriction, including
164.13 +// without limitation the rights to use, copy, modify, merge, publish,
164.14 +// distribute, sublicense, and/or sell copies of the Software, and to
164.15 +// permit persons to whom the Software is furnished to do so, subject to
164.16 +// the following conditions:
164.17 +//
164.18 +// The above copyright notice and this permission notice shall be included
164.19 +// in all copies or substantial portions of the Software.
164.20 +//
164.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
164.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
164.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
164.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
164.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
164.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
164.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
164.28 +// </copyright>
164.29 +// <summary>
164.30 +// Base class for BarSeries and ColumnSeries.
164.31 +// </summary>
164.32 +// --------------------------------------------------------------------------------------------------------------------
164.33 +namespace OxyPlot.Series
164.34 +{
164.35 + using System;
164.36 + using System.Collections.Generic;
164.37 + using System.Linq;
164.38 +
164.39 + using OxyPlot.Axes;
164.40 +
164.41 + /// <summary>
164.42 + /// Base class for BarSeries and ColumnSeries.
164.43 + /// </summary>
164.44 + public abstract class BarSeriesBase : CategorizedSeries, IStackableSeries
164.45 + {
164.46 + /// <summary>
164.47 + /// The default fill color.
164.48 + /// </summary>
164.49 + private OxyColor defaultFillColor;
164.50 +
164.51 + /// <summary>
164.52 + /// Initializes a new instance of the <see cref="BarSeriesBase"/> class.
164.53 + /// </summary>
164.54 + protected BarSeriesBase()
164.55 + {
164.56 + this.StrokeColor = OxyColors.Black;
164.57 + this.StrokeThickness = 0;
164.58 + this.TrackerFormatString = "{0}, {1}: {2}";
164.59 + this.LabelMargin = 2;
164.60 + this.StackGroup = string.Empty;
164.61 + }
164.62 +
164.63 + /// <summary>
164.64 + /// Gets or sets the base value.
164.65 + /// </summary>
164.66 + /// <value>
164.67 + /// The base value.
164.68 + /// </value>
164.69 + public double BaseValue { get; set; }
164.70 +
164.71 + /// <summary>
164.72 + /// Gets or sets the color field.
164.73 + /// </summary>
164.74 + public string ColorField { get; set; }
164.75 +
164.76 + /// <summary>
164.77 + /// Gets or sets the color of the interior of the bars.
164.78 + /// </summary>
164.79 + /// <value>
164.80 + /// The color.
164.81 + /// </value>
164.82 + public OxyColor FillColor { get; set; }
164.83 +
164.84 + /// <summary>
164.85 + /// Gets the actual fill color.
164.86 + /// </summary>
164.87 + /// <value>The actual color.</value>
164.88 + public OxyColor ActualFillColor
164.89 + {
164.90 + get { return this.FillColor ?? this.defaultFillColor; }
164.91 + }
164.92 +
164.93 + /// <summary>
164.94 + /// Gets or sets a value indicating whether this bar series is stacked.
164.95 + /// </summary>
164.96 + public bool IsStacked { get; set; }
164.97 +
164.98 + /// <summary>
164.99 + /// Gets or sets the label format string.
164.100 + /// </summary>
164.101 + /// <value>
164.102 + /// The label format string.
164.103 + /// </value>
164.104 + public string LabelFormatString { get; set; }
164.105 +
164.106 + /// <summary>
164.107 + /// Gets or sets the label margins.
164.108 + /// </summary>
164.109 + public double LabelMargin { get; set; }
164.110 +
164.111 + /// <summary>
164.112 + /// Gets or sets label placements.
164.113 + /// </summary>
164.114 + public LabelPlacement LabelPlacement { get; set; }
164.115 +
164.116 + /// <summary>
164.117 + /// Gets or sets the color of the interior of the bars when the value is negative.
164.118 + /// </summary>
164.119 + /// <value>
164.120 + /// The color.
164.121 + /// </value>
164.122 + public OxyColor NegativeFillColor { get; set; }
164.123 +
164.124 + /// <summary>
164.125 + /// Gets or sets the stack index indication to which stack the series belongs. Default is 0. Hence, all stacked series belong to the same stack.
164.126 + /// </summary>
164.127 + public string StackGroup { get; set; }
164.128 +
164.129 + /// <summary>
164.130 + /// Gets or sets the color of the border around the bars.
164.131 + /// </summary>
164.132 + /// <value>
164.133 + /// The color of the stroke.
164.134 + /// </value>
164.135 + public OxyColor StrokeColor { get; set; }
164.136 +
164.137 + /// <summary>
164.138 + /// Gets or sets the thickness of the bar border strokes.
164.139 + /// </summary>
164.140 + /// <value>
164.141 + /// The stroke thickness.
164.142 + /// </value>
164.143 + public double StrokeThickness { get; set; }
164.144 +
164.145 + /// <summary>
164.146 + /// Gets or sets the value field.
164.147 + /// </summary>
164.148 + public string ValueField { get; set; }
164.149 +
164.150 + /// <summary>
164.151 + /// Gets or sets the valid items
164.152 + /// </summary>
164.153 + protected internal IList<BarItemBase> ValidItems { get; set; }
164.154 +
164.155 + /// <summary>
164.156 + /// Gets or sets the dictionary which stores the index-inversion for the valid items
164.157 + /// </summary>
164.158 + protected internal Dictionary<int, int> ValidItemsIndexInversion { get; set; }
164.159 +
164.160 + /// <summary>
164.161 + /// Gets or sets the actual rectangles for the bars.
164.162 + /// </summary>
164.163 + protected IList<OxyRect> ActualBarRectangles { get; set; }
164.164 +
164.165 + /// <summary>
164.166 + /// Gets the nearest point.
164.167 + /// </summary>
164.168 + /// <param name="point">
164.169 + /// The point.
164.170 + /// </param>
164.171 + /// <param name="interpolate">
164.172 + /// interpolate if set to <c>true</c> .
164.173 + /// </param>
164.174 + /// <returns>
164.175 + /// A TrackerHitResult for the current hit.
164.176 + /// </returns>
164.177 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
164.178 + {
164.179 + if (this.ActualBarRectangles == null || this.ValidItems == null)
164.180 + {
164.181 + return null;
164.182 + }
164.183 +
164.184 + var i = 0;
164.185 + foreach (var rectangle in this.ActualBarRectangles)
164.186 + {
164.187 + if (rectangle.Contains(point))
164.188 + {
164.189 + var categoryIndex = this.ValidItems[i].GetCategoryIndex(i);
164.190 +
164.191 + var dp = new DataPoint(categoryIndex, this.ValidItems[i].Value);
164.192 + var item = this.GetItem(this.ValidItemsIndexInversion[i]);
164.193 + var text = this.GetTrackerText(item, categoryIndex);
164.194 + return new TrackerHitResult(this, dp, point, item, i, text);
164.195 + }
164.196 +
164.197 + i++;
164.198 + }
164.199 +
164.200 + return null;
164.201 + }
164.202 +
164.203 + /// <summary>
164.204 + /// Renders the series on the specified rendering context.
164.205 + /// </summary>
164.206 + /// <param name="rc">
164.207 + /// The rendering context.
164.208 + /// </param>
164.209 + /// <param name="model">
164.210 + /// The model.
164.211 + /// </param>
164.212 + public override void Render(IRenderContext rc, PlotModel model)
164.213 + {
164.214 + this.ActualBarRectangles = new List<OxyRect>();
164.215 +
164.216 + if (this.ValidItems == null || this.ValidItems.Count == 0)
164.217 + {
164.218 + return;
164.219 + }
164.220 +
164.221 + var clippingRect = this.GetClippingRect();
164.222 + var categoryAxis = this.GetCategoryAxis();
164.223 +
164.224 + var actualBarWidth = this.GetActualBarWidth();
164.225 + var stackIndex = this.IsStacked ? categoryAxis.StackIndexMapping[this.StackGroup] : 0;
164.226 + for (var i = 0; i < this.ValidItems.Count; i++)
164.227 + {
164.228 + var item = this.ValidItems[i];
164.229 + var categoryIndex = this.ValidItems[i].GetCategoryIndex(i);
164.230 +
164.231 + var value = item.Value;
164.232 +
164.233 + // Get base- and topValue
164.234 + var baseValue = double.NaN;
164.235 + if (this.IsStacked)
164.236 + {
164.237 + baseValue = value < 0
164.238 + ? categoryAxis.NegativeBaseValues[stackIndex, categoryIndex]
164.239 + : categoryAxis.PositiveBaseValues[stackIndex, categoryIndex];
164.240 + }
164.241 +
164.242 + if (double.IsNaN(baseValue))
164.243 + {
164.244 + baseValue = this.BaseValue;
164.245 + }
164.246 +
164.247 + var topValue = this.IsStacked ? baseValue + value : value;
164.248 +
164.249 + // Calculate offset
164.250 + double categoryValue;
164.251 + if (this.IsStacked)
164.252 + {
164.253 + categoryValue = categoryAxis.GetCategoryValue(categoryIndex, stackIndex, actualBarWidth);
164.254 + }
164.255 + else
164.256 + {
164.257 + categoryValue = categoryIndex - 0.5 + categoryAxis.BarOffset[categoryIndex];
164.258 + }
164.259 +
164.260 + if (this.IsStacked)
164.261 + {
164.262 + if (value < 0)
164.263 + {
164.264 + categoryAxis.NegativeBaseValues[stackIndex, categoryIndex] = topValue;
164.265 + }
164.266 + else
164.267 + {
164.268 + categoryAxis.PositiveBaseValues[stackIndex, categoryIndex] = topValue;
164.269 + }
164.270 + }
164.271 +
164.272 + var rect = this.GetRectangle(baseValue, topValue, categoryValue, categoryValue + actualBarWidth);
164.273 + this.ActualBarRectangles.Add(rect);
164.274 +
164.275 + this.RenderItem(rc, clippingRect, topValue, categoryValue, actualBarWidth, item, rect);
164.276 +
164.277 + if (this.LabelFormatString != null)
164.278 + {
164.279 + this.RenderLabel(rc, clippingRect, rect, value, i);
164.280 + }
164.281 +
164.282 + if (!this.IsStacked)
164.283 + {
164.284 + categoryAxis.BarOffset[categoryIndex] += actualBarWidth;
164.285 + }
164.286 + }
164.287 + }
164.288 +
164.289 + /// <summary>
164.290 + /// Renders the legend symbol on the specified rendering context.
164.291 + /// </summary>
164.292 + /// <param name="rc">
164.293 + /// The rendering context.
164.294 + /// </param>
164.295 + /// <param name="legendBox">
164.296 + /// The legend rectangle.
164.297 + /// </param>
164.298 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
164.299 + {
164.300 + var xmid = (legendBox.Left + legendBox.Right) / 2;
164.301 + var ymid = (legendBox.Top + legendBox.Bottom) / 2;
164.302 + var height = (legendBox.Bottom - legendBox.Top) * 0.8;
164.303 + var width = height;
164.304 + rc.DrawRectangleAsPolygon(
164.305 + new OxyRect(xmid - (0.5 * width), ymid - (0.5 * height), width, height),
164.306 + this.GetSelectableColor(this.ActualFillColor),
164.307 + this.StrokeColor,
164.308 + this.StrokeThickness);
164.309 + }
164.310 +
164.311 + /// <summary>
164.312 + /// Check if the data series is using the specified axis.
164.313 + /// </summary>
164.314 + /// <param name="axis">
164.315 + /// An axis which should be checked if used
164.316 + /// </param>
164.317 + /// <returns>
164.318 + /// True if the axis is in use.
164.319 + /// </returns>
164.320 + protected internal override bool IsUsing(Axis axis)
164.321 + {
164.322 + return this.XAxis == axis || this.YAxis == axis;
164.323 + }
164.324 +
164.325 + /// <summary>
164.326 + /// The set default values.
164.327 + /// </summary>
164.328 + /// <param name="model">
164.329 + /// The model.
164.330 + /// </param>
164.331 + protected internal override void SetDefaultValues(PlotModel model)
164.332 + {
164.333 + if (this.FillColor == null)
164.334 + {
164.335 + this.defaultFillColor = model.GetDefaultColor();
164.336 + }
164.337 + }
164.338 +
164.339 + /// <summary>
164.340 + /// The update axis max min.
164.341 + /// </summary>
164.342 + protected internal override void UpdateAxisMaxMin()
164.343 + {
164.344 + var valueAxis = this.GetValueAxis();
164.345 + if (valueAxis.IsVertical())
164.346 + {
164.347 + valueAxis.Include(this.MinY);
164.348 + valueAxis.Include(this.MaxY);
164.349 + }
164.350 + else
164.351 + {
164.352 + valueAxis.Include(this.MinX);
164.353 + valueAxis.Include(this.MaxX);
164.354 + }
164.355 + }
164.356 +
164.357 + /// <summary>
164.358 + /// Updates the maximum/minimum value on the value axis from the bar values.
164.359 + /// </summary>
164.360 + protected internal override void UpdateMaxMin()
164.361 + {
164.362 + base.UpdateMaxMin();
164.363 +
164.364 + if (this.ValidItems == null || this.ValidItems.Count == 0)
164.365 + {
164.366 + return;
164.367 + }
164.368 +
164.369 + var categoryAxis = this.GetCategoryAxis();
164.370 +
164.371 + double minValue = double.MaxValue, maxValue = double.MinValue;
164.372 + if (this.IsStacked)
164.373 + {
164.374 + var labels = this.GetCategoryAxis().Labels;
164.375 + for (var i = 0; i < labels.Count; i++)
164.376 + {
164.377 + int j = 0;
164.378 + var values =
164.379 + this.ValidItems.Where(item => item.GetCategoryIndex(j++) == i).Select(item => item.Value).Concat(new[] { 0d }).ToList();
164.380 + var minTemp = values.Where(v => v <= 0).Sum();
164.381 + var maxTemp = values.Where(v => v >= 0).Sum();
164.382 +
164.383 + int stackIndex = categoryAxis.StackIndexMapping[this.StackGroup];
164.384 + var stackedMinValue = categoryAxis.MinValue[stackIndex, i];
164.385 + if (!double.IsNaN(stackedMinValue))
164.386 + {
164.387 + minTemp += stackedMinValue;
164.388 + }
164.389 +
164.390 + categoryAxis.MinValue[stackIndex, i] = minTemp;
164.391 +
164.392 + var stackedMaxValue = categoryAxis.MaxValue[stackIndex, i];
164.393 + if (!double.IsNaN(stackedMaxValue))
164.394 + {
164.395 + maxTemp += stackedMaxValue;
164.396 + }
164.397 +
164.398 + categoryAxis.MaxValue[stackIndex, i] = maxTemp;
164.399 +
164.400 + minValue = Math.Min(minValue, minTemp + this.BaseValue);
164.401 + maxValue = Math.Max(maxValue, maxTemp + this.BaseValue);
164.402 + }
164.403 + }
164.404 + else
164.405 + {
164.406 + var values = this.ValidItems.Select(item => item.Value).Concat(new[] { 0d }).ToList();
164.407 + minValue = values.Min();
164.408 + maxValue = values.Max();
164.409 + if (this.BaseValue < minValue)
164.410 + {
164.411 + minValue = this.BaseValue;
164.412 + }
164.413 +
164.414 + if (this.BaseValue > maxValue)
164.415 + {
164.416 + maxValue = this.BaseValue;
164.417 + }
164.418 + }
164.419 +
164.420 + var valueAxis = this.GetValueAxis();
164.421 + if (valueAxis.IsVertical())
164.422 + {
164.423 + this.MinY = minValue;
164.424 + this.MaxY = maxValue;
164.425 + }
164.426 + else
164.427 + {
164.428 + this.MinX = minValue;
164.429 + this.MaxX = maxValue;
164.430 + }
164.431 + }
164.432 +
164.433 + /// <summary>
164.434 + /// Updates the valid items
164.435 + /// </summary>
164.436 + protected internal override void UpdateValidData()
164.437 + {
164.438 + this.ValidItems = new List<BarItemBase>();
164.439 + this.ValidItemsIndexInversion = new Dictionary<int, int>();
164.440 + var categories = this.GetCategoryAxis().Labels.Count;
164.441 + var valueAxis = this.GetValueAxis();
164.442 +
164.443 + int i = 0;
164.444 + foreach (var item in this.GetItems())
164.445 + {
164.446 + var barSeriesItem = item as BarItemBase;
164.447 +
164.448 + if (barSeriesItem != null && item.GetCategoryIndex(i) < categories
164.449 + && valueAxis.IsValidValue(barSeriesItem.Value))
164.450 + {
164.451 + this.ValidItemsIndexInversion.Add(this.ValidItems.Count, i);
164.452 + this.ValidItems.Add(barSeriesItem);
164.453 + }
164.454 +
164.455 + i++;
164.456 + }
164.457 + }
164.458 +
164.459 + /// <summary>
164.460 + /// Gets the rectangle for the specified values.
164.461 + /// </summary>
164.462 + /// <param name="baseValue">
164.463 + /// The base value of the bar
164.464 + /// </param>
164.465 + /// <param name="topValue">
164.466 + /// The top value of the bar
164.467 + /// </param>
164.468 + /// <param name="beginValue">
164.469 + /// The begin value of the bar
164.470 + /// </param>
164.471 + /// <param name="endValue">
164.472 + /// The end value of the bar
164.473 + /// </param>
164.474 + /// <returns>
164.475 + /// The rectangle.
164.476 + /// </returns>
164.477 + protected abstract OxyRect GetRectangle(double baseValue, double topValue, double beginValue, double endValue);
164.478 +
164.479 + /// <summary>
164.480 + /// Gets the tracker text for the specified item.
164.481 + /// </summary>
164.482 + /// <param name="item">
164.483 + /// The item.
164.484 + /// </param>
164.485 + /// <param name="categoryIndex">
164.486 + /// Category index of the item.
164.487 + /// </param>
164.488 + /// <returns>
164.489 + /// The tracker text.
164.490 + /// </returns>
164.491 + protected virtual string GetTrackerText(object item, int categoryIndex)
164.492 + {
164.493 + var barItem = item as BarItemBase;
164.494 + if (barItem == null)
164.495 + {
164.496 + return null;
164.497 + }
164.498 +
164.499 + var categoryAxis = this.GetCategoryAxis();
164.500 +
164.501 + var text = StringHelper.Format(
164.502 + this.ActualCulture,
164.503 + this.TrackerFormatString,
164.504 + item,
164.505 + this.Title,
164.506 + categoryAxis.FormatValueForTracker(categoryIndex),
164.507 + barItem.Value);
164.508 + return text;
164.509 + }
164.510 +
164.511 + /// <summary>
164.512 + /// Gets the value axis.
164.513 + /// </summary>
164.514 + /// <returns>
164.515 + /// The value axis.
164.516 + /// </returns>
164.517 + protected abstract Axis GetValueAxis();
164.518 +
164.519 + /// <summary>
164.520 + /// Checks if the specified value is valid.
164.521 + /// </summary>
164.522 + /// <param name="v">
164.523 + /// The value.
164.524 + /// </param>
164.525 + /// <param name="yaxis">
164.526 + /// The y axis.
164.527 + /// </param>
164.528 + /// <returns>
164.529 + /// True if the value is valid.
164.530 + /// </returns>
164.531 + protected virtual bool IsValidPoint(double v, Axis yaxis)
164.532 + {
164.533 + return !double.IsNaN(v) && !double.IsInfinity(v);
164.534 + }
164.535 +
164.536 + /// <summary>
164.537 + /// Renders the bar/column item.
164.538 + /// </summary>
164.539 + /// <param name="rc">
164.540 + /// The render context.
164.541 + /// </param>
164.542 + /// <param name="clippingRect">
164.543 + /// The clipping rectangle.
164.544 + /// </param>
164.545 + /// <param name="topValue">
164.546 + /// The end value of the bar.
164.547 + /// </param>
164.548 + /// <param name="categoryValue">
164.549 + /// The category value.
164.550 + /// </param>
164.551 + /// <param name="actualBarWidth">
164.552 + /// The actual width of the bar.
164.553 + /// </param>
164.554 + /// <param name="item">
164.555 + /// The item.
164.556 + /// </param>
164.557 + /// <param name="rect">
164.558 + /// The rectangle of the bar.
164.559 + /// </param>
164.560 + protected virtual void RenderItem(
164.561 + IRenderContext rc,
164.562 + OxyRect clippingRect,
164.563 + double topValue,
164.564 + double categoryValue,
164.565 + double actualBarWidth,
164.566 + BarItemBase item,
164.567 + OxyRect rect)
164.568 + {
164.569 + // Get the color of the item
164.570 + var actualFillColor = item.Color;
164.571 + if (actualFillColor == null)
164.572 + {
164.573 + actualFillColor = this.ActualFillColor;
164.574 + if (item.Value < 0 && this.NegativeFillColor != null)
164.575 + {
164.576 + actualFillColor = this.NegativeFillColor;
164.577 + }
164.578 + }
164.579 +
164.580 + rc.DrawClippedRectangleAsPolygon(
164.581 + rect, clippingRect, this.GetSelectableFillColor(actualFillColor), this.StrokeColor, this.StrokeThickness);
164.582 + }
164.583 +
164.584 + /// <summary>
164.585 + /// Renders the item label.
164.586 + /// </summary>
164.587 + /// <param name="rc">
164.588 + /// The render context
164.589 + /// </param>
164.590 + /// <param name="clippingRect">
164.591 + /// The clipping rectangle
164.592 + /// </param>
164.593 + /// <param name="rect">
164.594 + /// The rectangle of the item.
164.595 + /// </param>
164.596 + /// <param name="value">
164.597 + /// The value of the label.
164.598 + /// </param>
164.599 + /// <param name="index">
164.600 + /// The index of the bar item.
164.601 + /// </param>
164.602 + protected abstract void RenderLabel(
164.603 + IRenderContext rc, OxyRect clippingRect, OxyRect rect, double value, int index);
164.604 +
164.605 + }
164.606 +}
164.607 \ No newline at end of file
165.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
165.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/BarSeriesBase{T}.cs Sat Jun 08 16:53:22 2013 +0000
165.3 @@ -0,0 +1,113 @@
165.4 +// --------------------------------------------------------------------------------------------------------------------
165.5 +// <copyright file="BarSeriesBase{T}.cs" company="OxyPlot">
165.6 +// The MIT License (MIT)
165.7 +//
165.8 +// Copyright (c) 2012 Oystein Bjorke
165.9 +//
165.10 +// Permission is hereby granted, free of charge, to any person obtaining a
165.11 +// copy of this software and associated documentation files (the
165.12 +// "Software"), to deal in the Software without restriction, including
165.13 +// without limitation the rights to use, copy, modify, merge, publish,
165.14 +// distribute, sublicense, and/or sell copies of the Software, and to
165.15 +// permit persons to whom the Software is furnished to do so, subject to
165.16 +// the following conditions:
165.17 +//
165.18 +// The above copyright notice and this permission notice shall be included
165.19 +// in all copies or substantial portions of the Software.
165.20 +//
165.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
165.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
165.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
165.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
165.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
165.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
165.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
165.28 +// </copyright>
165.29 +// <summary>
165.30 +// Generic base class that provides common properties and methods for the BarSeries and ColumnSeries.
165.31 +// </summary>
165.32 +// --------------------------------------------------------------------------------------------------------------------
165.33 +namespace OxyPlot.Series
165.34 +{
165.35 + using System;
165.36 + using System.Collections;
165.37 + using System.Collections.Generic;
165.38 + using System.Linq;
165.39 +
165.40 + /// <summary>
165.41 + /// Generic base class that provides common properties and methods for the BarSeries and ColumnSeries.
165.42 + /// </summary>
165.43 + /// <typeparam name="T">
165.44 + /// The type of the items.
165.45 + /// </typeparam>
165.46 + public abstract class BarSeriesBase<T> : BarSeriesBase
165.47 + where T : BarItemBase, new()
165.48 + {
165.49 + /// <summary>
165.50 + /// Initializes a new instance of the <see cref="BarSeriesBase{T}"/> class. Initializes a new instance of the <see cref="BarSeriesBase<T>"/> class.
165.51 + /// </summary>
165.52 + protected BarSeriesBase()
165.53 + {
165.54 + this.Items = new List<T>();
165.55 + }
165.56 +
165.57 + /// <summary>
165.58 + /// Gets the items.
165.59 + /// </summary>
165.60 + /// <value>
165.61 + /// The items.
165.62 + /// </value>
165.63 + public IList<T> Items { get; private set; }
165.64 +
165.65 + /// <summary>
165.66 + /// Gets the items of this series.
165.67 + /// </summary>
165.68 + /// <returns>
165.69 + /// The items.
165.70 + /// </returns>
165.71 + protected internal override IList<CategorizedItem> GetItems()
165.72 + {
165.73 + return this.Items.Cast<CategorizedItem>().ToList();
165.74 + }
165.75 +
165.76 + /// <summary>
165.77 + /// Updates the data.
165.78 + /// </summary>
165.79 + protected internal override void UpdateData()
165.80 + {
165.81 + if (this.ItemsSource == null)
165.82 + {
165.83 + return;
165.84 + }
165.85 +
165.86 + var dest = new List<T>();
165.87 +
165.88 + // Using reflection to add points
165.89 + var filler = new ListFiller<T>();
165.90 + filler.Add(this.ValueField, (item, value) => item.Value = Convert.ToDouble(value));
165.91 + filler.Add(this.ColorField, (item, value) => item.Color = (OxyColor)value);
165.92 + filler.Fill(dest, this.ItemsSource);
165.93 + this.Items = dest;
165.94 + }
165.95 +
165.96 + /// <summary>
165.97 + /// Gets the item at the specified index.
165.98 + /// </summary>
165.99 + /// <param name="i">
165.100 + /// The index of the item.
165.101 + /// </param>
165.102 + /// <returns>
165.103 + /// The item of the index.
165.104 + /// </returns>
165.105 + protected override object GetItem(int i)
165.106 + {
165.107 + if (this.ItemsSource != null || this.Items == null || this.Items.Count == 0)
165.108 + {
165.109 + return base.GetItem(i);
165.110 + }
165.111 +
165.112 + return this.Items[i];
165.113 + }
165.114 +
165.115 + }
165.116 +}
165.117 \ No newline at end of file
166.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
166.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/CategorizedItem.cs Sat Jun 08 16:53:22 2013 +0000
166.3 @@ -0,0 +1,73 @@
166.4 +// --------------------------------------------------------------------------------------------------------------------
166.5 +// <copyright file="CategorizedItem.cs" company="OxyPlot">
166.6 +// The MIT License (MIT)
166.7 +//
166.8 +// Copyright (c) 2012 Oystein Bjorke
166.9 +//
166.10 +// Permission is hereby granted, free of charge, to any person obtaining a
166.11 +// copy of this software and associated documentation files (the
166.12 +// "Software"), to deal in the Software without restriction, including
166.13 +// without limitation the rights to use, copy, modify, merge, publish,
166.14 +// distribute, sublicense, and/or sell copies of the Software, and to
166.15 +// permit persons to whom the Software is furnished to do so, subject to
166.16 +// the following conditions:
166.17 +//
166.18 +// The above copyright notice and this permission notice shall be included
166.19 +// in all copies or substantial portions of the Software.
166.20 +//
166.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
166.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
166.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
166.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
166.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
166.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
166.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
166.28 +// </copyright>
166.29 +// <summary>
166.30 +// Represents an item in a CategorizedSeries.
166.31 +// </summary>
166.32 +// --------------------------------------------------------------------------------------------------------------------
166.33 +namespace OxyPlot.Series
166.34 +{
166.35 + /// <summary>
166.36 + /// Represents an item in a CategorizedSeries.
166.37 + /// </summary>
166.38 + public abstract class CategorizedItem
166.39 + {
166.40 + /// <summary>
166.41 + /// Initializes a new instance of the <see cref="CategorizedItem"/> class. Initializes a new instance of the <see cref="CategorizedItem"/> class.
166.42 + /// </summary>
166.43 + protected CategorizedItem()
166.44 + {
166.45 + this.CategoryIndex = -1;
166.46 + }
166.47 +
166.48 + /// <summary>
166.49 + /// Gets or sets the index of the category.
166.50 + /// </summary>
166.51 + /// <value>
166.52 + /// The index of the category.
166.53 + /// </value>
166.54 + public int CategoryIndex { get; set; }
166.55 +
166.56 + /// <summary>
166.57 + /// Gets the index of the category.
166.58 + /// </summary>
166.59 + /// <param name="defaultIndex">
166.60 + /// The default index.
166.61 + /// </param>
166.62 + /// <returns>
166.63 + /// The index.
166.64 + /// </returns>
166.65 + internal int GetCategoryIndex(int defaultIndex)
166.66 + {
166.67 + if (this.CategoryIndex < 0)
166.68 + {
166.69 + return defaultIndex;
166.70 + }
166.71 +
166.72 + return this.CategoryIndex;
166.73 + }
166.74 +
166.75 + }
166.76 +}
166.77 \ No newline at end of file
167.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
167.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/CategorizedSeries.cs Sat Jun 08 16:53:22 2013 +0000
167.3 @@ -0,0 +1,83 @@
167.4 +// --------------------------------------------------------------------------------------------------------------------
167.5 +// <copyright file="CategorizedSeries.cs" company="OxyPlot">
167.6 +// The MIT License (MIT)
167.7 +//
167.8 +// Copyright (c) 2012 Oystein Bjorke
167.9 +//
167.10 +// Permission is hereby granted, free of charge, to any person obtaining a
167.11 +// copy of this software and associated documentation files (the
167.12 +// "Software"), to deal in the Software without restriction, including
167.13 +// without limitation the rights to use, copy, modify, merge, publish,
167.14 +// distribute, sublicense, and/or sell copies of the Software, and to
167.15 +// permit persons to whom the Software is furnished to do so, subject to
167.16 +// the following conditions:
167.17 +//
167.18 +// The above copyright notice and this permission notice shall be included
167.19 +// in all copies or substantial portions of the Software.
167.20 +//
167.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
167.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
167.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
167.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
167.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
167.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
167.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
167.28 +// </copyright>
167.29 +// <summary>
167.30 +// Base class for series where the items are categorized.
167.31 +// </summary>
167.32 +// --------------------------------------------------------------------------------------------------------------------
167.33 +namespace OxyPlot.Series
167.34 +{
167.35 + using System.Collections.Generic;
167.36 +
167.37 + using OxyPlot.Axes;
167.38 +
167.39 + /// <summary>
167.40 + /// Base class for series where the items are categorized.
167.41 + /// </summary>
167.42 + public abstract class CategorizedSeries : XYAxisSeries
167.43 + {
167.44 + /// <summary>
167.45 + /// Gets or sets the width/height of the columns/bars (as a fraction of the available space).
167.46 + /// </summary>
167.47 + /// <returns>
167.48 + /// The fractional width.
167.49 + /// </returns>
167.50 + /// <value>
167.51 + /// The width of the bars.
167.52 + /// </value>
167.53 + /// <remarks>
167.54 + /// The available space will be determined by the GapWidth of the CategoryAxis used by this series.
167.55 + /// </remarks>
167.56 + internal abstract double GetBarWidth();
167.57 +
167.58 + /// <summary>
167.59 + /// Gets the items of this series.
167.60 + /// </summary>
167.61 + /// <returns>
167.62 + /// The items.
167.63 + /// </returns>
167.64 + protected internal abstract IList<CategorizedItem> GetItems();
167.65 +
167.66 + /// <summary>
167.67 + /// Gets the actual bar width/height of the items in this series.
167.68 + /// </summary>
167.69 + /// <returns>
167.70 + /// The width or height.
167.71 + /// </returns>
167.72 + /// <remarks>
167.73 + /// The actual width is also influenced by the GapWidth of the CategoryAxis used by this series.
167.74 + /// </remarks>
167.75 + protected abstract double GetActualBarWidth();
167.76 +
167.77 + /// <summary>
167.78 + /// Gets the category axis.
167.79 + /// </summary>
167.80 + /// <returns>
167.81 + /// The category axis.
167.82 + /// </returns>
167.83 + protected abstract CategoryAxis GetCategoryAxis();
167.84 +
167.85 + }
167.86 +}
167.87 \ No newline at end of file
168.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
168.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/ColumnItem.cs Sat Jun 08 16:53:22 2013 +0000
168.3 @@ -0,0 +1,64 @@
168.4 +// --------------------------------------------------------------------------------------------------------------------
168.5 +// <copyright file="ColumnItem.cs" company="OxyPlot">
168.6 +// The MIT License (MIT)
168.7 +//
168.8 +// Copyright (c) 2012 Oystein Bjorke
168.9 +//
168.10 +// Permission is hereby granted, free of charge, to any person obtaining a
168.11 +// copy of this software and associated documentation files (the
168.12 +// "Software"), to deal in the Software without restriction, including
168.13 +// without limitation the rights to use, copy, modify, merge, publish,
168.14 +// distribute, sublicense, and/or sell copies of the Software, and to
168.15 +// permit persons to whom the Software is furnished to do so, subject to
168.16 +// the following conditions:
168.17 +//
168.18 +// The above copyright notice and this permission notice shall be included
168.19 +// in all copies or substantial portions of the Software.
168.20 +//
168.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
168.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
168.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
168.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
168.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
168.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
168.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
168.28 +// </copyright>
168.29 +// <summary>
168.30 +// Represents an item used in the ColumnSeries.
168.31 +// </summary>
168.32 +// --------------------------------------------------------------------------------------------------------------------
168.33 +namespace OxyPlot.Series
168.34 +{
168.35 + /// <summary>
168.36 + /// Represents an item used in the ColumnSeries.
168.37 + /// </summary>
168.38 + public class ColumnItem : BarItemBase
168.39 + {
168.40 + /// <summary>
168.41 + /// Initializes a new instance of the <see cref="ColumnItem"/> class.
168.42 + /// </summary>
168.43 + public ColumnItem()
168.44 + {
168.45 + }
168.46 +
168.47 + /// <summary>
168.48 + /// Initializes a new instance of the <see cref="ColumnItem"/> class.
168.49 + /// </summary>
168.50 + /// <param name="value">
168.51 + /// The value.
168.52 + /// </param>
168.53 + /// <param name="categoryIndex">
168.54 + /// Index of the category.
168.55 + /// </param>
168.56 + /// <param name="color">
168.57 + /// The color.
168.58 + /// </param>
168.59 + public ColumnItem(double value, int categoryIndex = -1, OxyColor color = null)
168.60 + {
168.61 + this.Value = value;
168.62 + this.CategoryIndex = categoryIndex;
168.63 + this.Color = color;
168.64 + }
168.65 +
168.66 + }
168.67 +}
168.68 \ No newline at end of file
169.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
169.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/ColumnSeries.cs Sat Jun 08 16:53:22 2013 +0000
169.3 @@ -0,0 +1,198 @@
169.4 +// --------------------------------------------------------------------------------------------------------------------
169.5 +// <copyright file="ColumnSeries.cs" company="OxyPlot">
169.6 +// The MIT License (MIT)
169.7 +//
169.8 +// Copyright (c) 2012 Oystein Bjorke
169.9 +//
169.10 +// Permission is hereby granted, free of charge, to any person obtaining a
169.11 +// copy of this software and associated documentation files (the
169.12 +// "Software"), to deal in the Software without restriction, including
169.13 +// without limitation the rights to use, copy, modify, merge, publish,
169.14 +// distribute, sublicense, and/or sell copies of the Software, and to
169.15 +// permit persons to whom the Software is furnished to do so, subject to
169.16 +// the following conditions:
169.17 +//
169.18 +// The above copyright notice and this permission notice shall be included
169.19 +// in all copies or substantial portions of the Software.
169.20 +//
169.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
169.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
169.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
169.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
169.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
169.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
169.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
169.28 +// </copyright>
169.29 +// <summary>
169.30 +// Represents a series for clustered or stacked column charts.
169.31 +// </summary>
169.32 +// --------------------------------------------------------------------------------------------------------------------
169.33 +namespace OxyPlot.Series
169.34 +{
169.35 + using System;
169.36 +
169.37 + using OxyPlot.Axes;
169.38 +
169.39 + /// <summary>
169.40 + /// Represents a series for clustered or stacked column charts.
169.41 + /// </summary>
169.42 + public class ColumnSeries : BarSeriesBase<ColumnItem>
169.43 + {
169.44 + /// <summary>
169.45 + /// Initializes a new instance of the <see cref="ColumnSeries"/> class.
169.46 + /// </summary>
169.47 + public ColumnSeries()
169.48 + {
169.49 + this.ColumnWidth = 1;
169.50 + }
169.51 +
169.52 + /// <summary>
169.53 + /// Gets or sets the width of the column.
169.54 + /// </summary>
169.55 + /// <value>
169.56 + /// The width of the column.
169.57 + /// </value>
169.58 + public double ColumnWidth { get; set; }
169.59 +
169.60 + /// <summary>
169.61 + /// Gets or sets the width/height of the columns/bars (as a fraction of the available space).
169.62 + /// </summary>
169.63 + /// <returns>
169.64 + /// The fractional width.
169.65 + /// </returns>
169.66 + /// <value>
169.67 + /// The width of the bars.
169.68 + /// </value>
169.69 + /// <remarks>
169.70 + /// The available space will be determined by the GapWidth of the CategoryAxis used by this series.
169.71 + /// </remarks>
169.72 + internal override double GetBarWidth()
169.73 + {
169.74 + return this.ColumnWidth;
169.75 + }
169.76 +
169.77 + /// <summary>
169.78 + /// Gets the actual width/height of the items of this series.
169.79 + /// </summary>
169.80 + /// <returns>
169.81 + /// The width or height.
169.82 + /// </returns>
169.83 + /// <remarks>
169.84 + /// The actual width is also influenced by the GapWidth of the CategoryAxis used by this series.
169.85 + /// </remarks>
169.86 + protected override double GetActualBarWidth()
169.87 + {
169.88 + var categoryAxis = this.GetCategoryAxis();
169.89 + return this.ColumnWidth / (1 + categoryAxis.GapWidth) / categoryAxis.MaxWidth;
169.90 + }
169.91 +
169.92 + /// <summary>
169.93 + /// Gets the category axis.
169.94 + /// </summary>
169.95 + /// <returns>
169.96 + /// The category axis.
169.97 + /// </returns>
169.98 + protected override CategoryAxis GetCategoryAxis()
169.99 + {
169.100 + if (!(this.XAxis is CategoryAxis))
169.101 + {
169.102 + throw new Exception(
169.103 + "A ColumnSeries requires a CategoryAxis on the x-axis. Use a BarSeries if you want horizontal bars.");
169.104 + }
169.105 +
169.106 + return this.XAxis as CategoryAxis;
169.107 + }
169.108 +
169.109 + /// <summary>
169.110 + /// Gets the rectangle for the specified values.
169.111 + /// </summary>
169.112 + /// <param name="baseValue">
169.113 + /// The base value of the bar
169.114 + /// </param>
169.115 + /// <param name="topValue">
169.116 + /// The top value of the bar
169.117 + /// </param>
169.118 + /// <param name="beginValue">
169.119 + /// The begin value of the bar
169.120 + /// </param>
169.121 + /// <param name="endValue">
169.122 + /// The end value of the bar
169.123 + /// </param>
169.124 + /// <returns>
169.125 + /// The rectangle.
169.126 + /// </returns>
169.127 + protected override OxyRect GetRectangle(double baseValue, double topValue, double beginValue, double endValue)
169.128 + {
169.129 + return OxyRect.Create(this.Transform(beginValue, baseValue), this.Transform(endValue, topValue));
169.130 + }
169.131 +
169.132 + /// <summary>
169.133 + /// Gets the value axis.
169.134 + /// </summary>
169.135 + /// <returns>
169.136 + /// The value axis.
169.137 + /// </returns>
169.138 + protected override Axis GetValueAxis()
169.139 + {
169.140 + return this.YAxis;
169.141 + }
169.142 +
169.143 + /// <summary>
169.144 + /// Draws the label.
169.145 + /// </summary>
169.146 + /// <param name="rc">
169.147 + /// The render context.
169.148 + /// </param>
169.149 + /// <param name="clippingRect">
169.150 + /// The clipping rect.
169.151 + /// </param>
169.152 + /// <param name="rect">
169.153 + /// The rect.
169.154 + /// </param>
169.155 + /// <param name="value">
169.156 + /// The value.
169.157 + /// </param>
169.158 + /// <param name="i">
169.159 + /// The i.
169.160 + /// </param>
169.161 + protected override void RenderLabel(IRenderContext rc, OxyRect clippingRect, OxyRect rect, double value, int i)
169.162 + {
169.163 + var s = StringHelper.Format(
169.164 + this.ActualCulture, this.LabelFormatString, this.GetItem(this.ValidItemsIndexInversion[i]), value);
169.165 + ScreenPoint pt;
169.166 + VerticalAlignment va;
169.167 + switch (this.LabelPlacement)
169.168 + {
169.169 + case LabelPlacement.Inside:
169.170 + pt = new ScreenPoint((rect.Left + rect.Right) / 2, rect.Top + this.LabelMargin);
169.171 + va = VerticalAlignment.Top;
169.172 + break;
169.173 + case LabelPlacement.Middle:
169.174 + pt = new ScreenPoint((rect.Left + rect.Right) / 2, (rect.Bottom + rect.Top) / 2);
169.175 + va = VerticalAlignment.Middle;
169.176 + break;
169.177 + case LabelPlacement.Base:
169.178 + pt = new ScreenPoint((rect.Left + rect.Right) / 2, rect.Bottom - this.LabelMargin);
169.179 + va = VerticalAlignment.Bottom;
169.180 + break;
169.181 + default: // outside
169.182 + pt = new ScreenPoint((rect.Left + rect.Right) / 2, rect.Top - this.LabelMargin);
169.183 + va = VerticalAlignment.Bottom;
169.184 + break;
169.185 + }
169.186 +
169.187 + rc.DrawClippedText(
169.188 + clippingRect,
169.189 + pt,
169.190 + s,
169.191 + this.ActualTextColor,
169.192 + this.ActualFont,
169.193 + this.ActualFontSize,
169.194 + this.ActualFontWeight,
169.195 + 0,
169.196 + HorizontalAlignment.Center,
169.197 + va);
169.198 + }
169.199 +
169.200 + }
169.201 +}
169.202 \ No newline at end of file
170.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
170.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/ErrorColumnItem.cs Sat Jun 08 16:53:22 2013 +0000
170.3 @@ -0,0 +1,96 @@
170.4 +// --------------------------------------------------------------------------------------------------------------------
170.5 +// <copyright file="ErrorColumnItem.cs" company="OxyPlot">
170.6 +// The MIT License (MIT)
170.7 +//
170.8 +// Copyright (c) 2012 Oystein Bjorke
170.9 +//
170.10 +// Permission is hereby granted, free of charge, to any person obtaining a
170.11 +// copy of this software and associated documentation files (the
170.12 +// "Software"), to deal in the Software without restriction, including
170.13 +// without limitation the rights to use, copy, modify, merge, publish,
170.14 +// distribute, sublicense, and/or sell copies of the Software, and to
170.15 +// permit persons to whom the Software is furnished to do so, subject to
170.16 +// the following conditions:
170.17 +//
170.18 +// The above copyright notice and this permission notice shall be included
170.19 +// in all copies or substantial portions of the Software.
170.20 +//
170.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
170.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
170.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
170.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
170.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
170.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
170.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
170.28 +// </copyright>
170.29 +// <summary>
170.30 +// Represents an item used in the ErrorColumnSeries.
170.31 +// </summary>
170.32 +// --------------------------------------------------------------------------------------------------------------------
170.33 +namespace OxyPlot.Series
170.34 +{
170.35 + /// <summary>
170.36 + /// Represents an item used in the ErrorColumnSeries.
170.37 + /// </summary>
170.38 + public class ErrorColumnItem : ColumnItem
170.39 + {
170.40 + /// <summary>
170.41 + /// Initializes a new instance of the <see cref="ErrorColumnItem"/> class.
170.42 + /// </summary>
170.43 + public ErrorColumnItem()
170.44 + {
170.45 + }
170.46 +
170.47 + /// <summary>
170.48 + /// Initializes a new instance of the <see cref="ErrorColumnItem"/> class.
170.49 + /// </summary>
170.50 + /// <param name="value">
170.51 + /// The value.
170.52 + /// </param>
170.53 + /// <param name="error">
170.54 + /// The error.
170.55 + /// </param>
170.56 + /// <param name="categoryIndex">
170.57 + /// Index of the category.
170.58 + /// </param>
170.59 + /// <param name="color">
170.60 + /// The color.
170.61 + /// </param>
170.62 + public ErrorColumnItem(double value, double error, int categoryIndex = -1, OxyColor color = null)
170.63 + {
170.64 + this.Value = value;
170.65 + this.Error = error;
170.66 + this.CategoryIndex = categoryIndex;
170.67 + this.Color = color;
170.68 + }
170.69 +
170.70 + /// <summary>
170.71 + /// Gets or sets the error of the item.
170.72 + /// </summary>
170.73 + public double Error { get; set; }
170.74 +
170.75 + /// <summary>
170.76 + /// Returns c# code that generates this instance.
170.77 + /// </summary>
170.78 + /// <returns>
170.79 + /// C# code.
170.80 + /// </returns>
170.81 + public override string ToCode()
170.82 + {
170.83 + if (this.Color != null)
170.84 + {
170.85 + return CodeGenerator.FormatConstructor(
170.86 + this.GetType(), "{0},{1},{2},{3}", this.Value, this.Error, this.CategoryIndex, this.Color.ToCode());
170.87 + }
170.88 +
170.89 + if (this.CategoryIndex != -1)
170.90 + {
170.91 + return CodeGenerator.FormatConstructor(
170.92 + this.GetType(), "{0},{1},{2}", this.Value, this.Error, this.CategoryIndex);
170.93 + }
170.94 +
170.95 + return CodeGenerator.FormatConstructor(this.GetType(), "{0},{1}", this.Value, this.Error);
170.96 + }
170.97 +
170.98 + }
170.99 +}
170.100 \ No newline at end of file
171.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
171.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/ErrorColumnSeries.cs Sat Jun 08 16:53:22 2013 +0000
171.3 @@ -0,0 +1,240 @@
171.4 +// --------------------------------------------------------------------------------------------------------------------
171.5 +// <copyright file="ErrorColumnSeries.cs" company="OxyPlot">
171.6 +// The MIT License (MIT)
171.7 +//
171.8 +// Copyright (c) 2012 Oystein Bjorke
171.9 +//
171.10 +// Permission is hereby granted, free of charge, to any person obtaining a
171.11 +// copy of this software and associated documentation files (the
171.12 +// "Software"), to deal in the Software without restriction, including
171.13 +// without limitation the rights to use, copy, modify, merge, publish,
171.14 +// distribute, sublicense, and/or sell copies of the Software, and to
171.15 +// permit persons to whom the Software is furnished to do so, subject to
171.16 +// the following conditions:
171.17 +//
171.18 +// The above copyright notice and this permission notice shall be included
171.19 +// in all copies or substantial portions of the Software.
171.20 +//
171.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
171.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
171.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
171.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
171.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
171.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
171.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
171.28 +// </copyright>
171.29 +// <summary>
171.30 +// Represents a series for clustered or stacked column charts with an error value.
171.31 +// </summary>
171.32 +// --------------------------------------------------------------------------------------------------------------------
171.33 +namespace OxyPlot.Series
171.34 +{
171.35 + using System;
171.36 + using System.Collections.Generic;
171.37 + using System.Linq;
171.38 +
171.39 + /// <summary>
171.40 + /// Represents a series for clustered or stacked column charts with an error value.
171.41 + /// </summary>
171.42 + public class ErrorColumnSeries : ColumnSeries
171.43 + {
171.44 + /// <summary>
171.45 + /// Initializes a new instance of the <see cref="ErrorColumnSeries"/> class.
171.46 + /// </summary>
171.47 + public ErrorColumnSeries()
171.48 + {
171.49 + this.ErrorWidth = 0.4;
171.50 + this.ErrorStrokeThickness = 1;
171.51 + this.TrackerFormatString = "{0}, {1}: {2}, Error: {Error}";
171.52 + }
171.53 +
171.54 + /// <summary>
171.55 + /// Gets or sets the stroke thickness of the error line.
171.56 + /// </summary>
171.57 + /// <value>
171.58 + /// The stroke thickness of the error line.
171.59 + /// </value>
171.60 + public double ErrorStrokeThickness { get; set; }
171.61 +
171.62 + /// <summary>
171.63 + /// Gets or sets the width of the error end lines.
171.64 + /// </summary>
171.65 + /// <value>
171.66 + /// The width of the error end lines.
171.67 + /// </value>
171.68 + public double ErrorWidth { get; set; }
171.69 +
171.70 + /// <summary>
171.71 + /// Updates the maximum/minimum value on the value axis from the bar values.
171.72 + /// </summary>
171.73 + protected internal override void UpdateMaxMin()
171.74 + {
171.75 + base.UpdateMaxMin();
171.76 +
171.77 + //// Todo: refactor (lots of duplicate code here)
171.78 + if (this.ValidItems == null || this.ValidItems.Count == 0)
171.79 + {
171.80 + return;
171.81 + }
171.82 +
171.83 + var categoryAxis = this.GetCategoryAxis();
171.84 +
171.85 + double minValue = double.MaxValue, maxValue = double.MinValue;
171.86 + if (this.IsStacked)
171.87 + {
171.88 + var labels = this.GetCategoryAxis().Labels;
171.89 + for (var i = 0; i < labels.Count; i++)
171.90 + {
171.91 + int j = 0;
171.92 + var items = this.ValidItems.Where(item => item.GetCategoryIndex(j++) == i).ToList();
171.93 + var values = items.Select(item => item.Value).Concat(new[] { 0d }).ToList();
171.94 + var minTemp = values.Where(v => v <= 0).Sum();
171.95 + var maxTemp = values.Where(v => v >= 0).Sum() + ((ErrorColumnItem)items.Last()).Error;
171.96 +
171.97 + int stackIndex = categoryAxis.StackIndexMapping[this.StackGroup];
171.98 + var stackedMinValue = categoryAxis.MinValue[stackIndex, i];
171.99 + if (!double.IsNaN(stackedMinValue))
171.100 + {
171.101 + minTemp += stackedMinValue;
171.102 + }
171.103 +
171.104 + categoryAxis.MinValue[stackIndex, i] = minTemp;
171.105 +
171.106 + var stackedMaxValue = categoryAxis.MaxValue[stackIndex, i];
171.107 + if (!double.IsNaN(stackedMaxValue))
171.108 + {
171.109 + maxTemp += stackedMaxValue;
171.110 + }
171.111 +
171.112 + categoryAxis.MaxValue[stackIndex, i] = maxTemp;
171.113 +
171.114 + minValue = Math.Min(minValue, minTemp + this.BaseValue);
171.115 + maxValue = Math.Max(maxValue, maxTemp + this.BaseValue);
171.116 + }
171.117 + }
171.118 + else
171.119 + {
171.120 + var valuesMin =
171.121 + this.ValidItems.Select(item => item.Value - ((ErrorColumnItem)item).Error).Concat(new[] { 0d }).
171.122 + ToList();
171.123 + var valuesMax =
171.124 + this.ValidItems.Select(item => item.Value + ((ErrorColumnItem)item).Error).Concat(new[] { 0d }).
171.125 + ToList();
171.126 + minValue = valuesMin.Min();
171.127 + maxValue = valuesMax.Max();
171.128 + if (this.BaseValue < minValue)
171.129 + {
171.130 + minValue = this.BaseValue;
171.131 + }
171.132 +
171.133 + if (this.BaseValue > maxValue)
171.134 + {
171.135 + maxValue = this.BaseValue;
171.136 + }
171.137 + }
171.138 +
171.139 + var valueAxis = this.GetValueAxis();
171.140 + if (valueAxis.IsVertical())
171.141 + {
171.142 + this.MinY = minValue;
171.143 + this.MaxY = maxValue;
171.144 + }
171.145 + else
171.146 + {
171.147 + this.MinX = minValue;
171.148 + this.MaxX = maxValue;
171.149 + }
171.150 + }
171.151 +
171.152 + /// <summary>
171.153 + /// Renders the bar/column item.
171.154 + /// </summary>
171.155 + /// <param name="rc">
171.156 + /// The render context.
171.157 + /// </param>
171.158 + /// <param name="clippingRect">
171.159 + /// The clipping rectangle.
171.160 + /// </param>
171.161 + /// <param name="topValue">
171.162 + /// The end value of the bar.
171.163 + /// </param>
171.164 + /// <param name="categoryValue">
171.165 + /// The category value.
171.166 + /// </param>
171.167 + /// <param name="actualBarWidth">
171.168 + /// The actual width of the bar.
171.169 + /// </param>
171.170 + /// <param name="item">
171.171 + /// The item.
171.172 + /// </param>
171.173 + /// <param name="rect">
171.174 + /// The rectangle of the bar.
171.175 + /// </param>
171.176 + protected override void RenderItem(
171.177 + IRenderContext rc,
171.178 + OxyRect clippingRect,
171.179 + double topValue,
171.180 + double categoryValue,
171.181 + double actualBarWidth,
171.182 + BarItemBase item,
171.183 + OxyRect rect)
171.184 + {
171.185 + base.RenderItem(rc, clippingRect, topValue, categoryValue, actualBarWidth, item, rect);
171.186 +
171.187 + var errorItem = item as ErrorColumnItem;
171.188 + if (errorItem == null)
171.189 + {
171.190 + return;
171.191 + }
171.192 +
171.193 + // Render the error
171.194 + var lowerValue = topValue - errorItem.Error;
171.195 + var upperValue = topValue + errorItem.Error;
171.196 + var left = 0.5 - this.ErrorWidth / 2;
171.197 + var right = 0.5 + this.ErrorWidth / 2;
171.198 + var leftValue = categoryValue + (left * actualBarWidth);
171.199 + var middleValue = categoryValue + (0.5 * actualBarWidth);
171.200 + var rightValue = categoryValue + (right * actualBarWidth);
171.201 +
171.202 + var lowerErrorPoint = this.Transform(middleValue, lowerValue);
171.203 + var upperErrorPoint = this.Transform(middleValue, upperValue);
171.204 + rc.DrawClippedLine(
171.205 + new List<ScreenPoint> { lowerErrorPoint, upperErrorPoint },
171.206 + clippingRect,
171.207 + 0,
171.208 + this.StrokeColor,
171.209 + this.ErrorStrokeThickness,
171.210 + LineStyle.Solid,
171.211 + OxyPenLineJoin.Miter,
171.212 + true);
171.213 +
171.214 + if (this.ErrorWidth > 0)
171.215 + {
171.216 + var lowerLeftErrorPoint = this.Transform(leftValue, lowerValue);
171.217 + var lowerRightErrorPoint = this.Transform(rightValue, lowerValue);
171.218 + rc.DrawClippedLine(
171.219 + new List<ScreenPoint> { lowerLeftErrorPoint, lowerRightErrorPoint },
171.220 + clippingRect,
171.221 + 0,
171.222 + this.StrokeColor,
171.223 + this.ErrorStrokeThickness,
171.224 + LineStyle.Solid,
171.225 + OxyPenLineJoin.Miter,
171.226 + true);
171.227 +
171.228 + var upperLeftErrorPoint = this.Transform(leftValue, upperValue);
171.229 + var upperRightErrorPoint = this.Transform(rightValue, upperValue);
171.230 + rc.DrawClippedLine(
171.231 + new List<ScreenPoint> { upperLeftErrorPoint, upperRightErrorPoint },
171.232 + clippingRect,
171.233 + 0,
171.234 + this.StrokeColor,
171.235 + this.ErrorStrokeThickness,
171.236 + LineStyle.Solid,
171.237 + OxyPenLineJoin.Miter,
171.238 + true);
171.239 + }
171.240 + }
171.241 +
171.242 + }
171.243 +}
171.244 \ No newline at end of file
172.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
172.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/IStackableSeries.cs Sat Jun 08 16:53:22 2013 +0000
172.3 @@ -0,0 +1,50 @@
172.4 +// --------------------------------------------------------------------------------------------------------------------
172.5 +// <copyright file="IStackableSeries.cs" company="OxyPlot">
172.6 +// The MIT License (MIT)
172.7 +//
172.8 +// Copyright (c) 2012 Oystein Bjorke
172.9 +//
172.10 +// Permission is hereby granted, free of charge, to any person obtaining a
172.11 +// copy of this software and associated documentation files (the
172.12 +// "Software"), to deal in the Software without restriction, including
172.13 +// without limitation the rights to use, copy, modify, merge, publish,
172.14 +// distribute, sublicense, and/or sell copies of the Software, and to
172.15 +// permit persons to whom the Software is furnished to do so, subject to
172.16 +// the following conditions:
172.17 +//
172.18 +// The above copyright notice and this permission notice shall be included
172.19 +// in all copies or substantial portions of the Software.
172.20 +//
172.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
172.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
172.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
172.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
172.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
172.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
172.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
172.28 +// </copyright>
172.29 +// <summary>
172.30 +// Specifies a series that can be stacked.
172.31 +// </summary>
172.32 +// --------------------------------------------------------------------------------------------------------------------
172.33 +namespace OxyPlot.Series
172.34 +{
172.35 + /// <summary>
172.36 + /// Defines properties for stacked series.
172.37 + /// </summary>
172.38 + public interface IStackableSeries
172.39 + {
172.40 + /// <summary>
172.41 + /// Gets a value indicating whether this series is stacked.
172.42 + /// </summary>
172.43 + bool IsStacked { get; }
172.44 +
172.45 + /// <summary>
172.46 + /// Gets the stack group.
172.47 + /// </summary>
172.48 + /// <value>
172.49 + /// The stack group.
172.50 + /// </value>
172.51 + string StackGroup { get; }
172.52 + }
172.53 +}
172.54 \ No newline at end of file
173.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
173.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/IntervalBarItem.cs Sat Jun 08 16:53:22 2013 +0000
173.3 @@ -0,0 +1,110 @@
173.4 +// --------------------------------------------------------------------------------------------------------------------
173.5 +// <copyright file="IntervalBarItem.cs" company="OxyPlot">
173.6 +// The MIT License (MIT)
173.7 +//
173.8 +// Copyright (c) 2012 Oystein Bjorke
173.9 +//
173.10 +// Permission is hereby granted, free of charge, to any person obtaining a
173.11 +// copy of this software and associated documentation files (the
173.12 +// "Software"), to deal in the Software without restriction, including
173.13 +// without limitation the rights to use, copy, modify, merge, publish,
173.14 +// distribute, sublicense, and/or sell copies of the Software, and to
173.15 +// permit persons to whom the Software is furnished to do so, subject to
173.16 +// the following conditions:
173.17 +//
173.18 +// The above copyright notice and this permission notice shall be included
173.19 +// in all copies or substantial portions of the Software.
173.20 +//
173.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
173.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
173.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
173.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
173.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
173.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
173.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
173.28 +// </copyright>
173.29 +// <summary>
173.30 +// Represents an item in an IntervalBarSeries.
173.31 +// </summary>
173.32 +// --------------------------------------------------------------------------------------------------------------------
173.33 +namespace OxyPlot.Series
173.34 +{
173.35 + /// <summary>
173.36 + /// Represents an item in an IntervalBarSeries.
173.37 + /// </summary>
173.38 + public class IntervalBarItem : CategorizedItem, ICodeGenerating
173.39 + {
173.40 + /// <summary>
173.41 + /// Initializes a new instance of the <see cref="IntervalBarItem"/> class.
173.42 + /// </summary>
173.43 + public IntervalBarItem()
173.44 + {
173.45 + }
173.46 +
173.47 + /// <summary>
173.48 + /// Initializes a new instance of the <see cref="IntervalBarItem"/> class.
173.49 + /// </summary>
173.50 + /// <param name="start">
173.51 + /// The start.
173.52 + /// </param>
173.53 + /// <param name="end">
173.54 + /// The end.
173.55 + /// </param>
173.56 + /// <param name="title">
173.57 + /// The title.
173.58 + /// </param>
173.59 + /// <param name="color">
173.60 + /// The color.
173.61 + /// </param>
173.62 + public IntervalBarItem(double start, double end, string title = null, OxyColor color = null)
173.63 + {
173.64 + this.Start = start;
173.65 + this.End = end;
173.66 + this.Title = title;
173.67 + this.Color = color;
173.68 + }
173.69 +
173.70 + /// <summary>
173.71 + /// Gets or sets the color.
173.72 + /// </summary>
173.73 + public OxyColor Color { get; set; }
173.74 +
173.75 + /// <summary>
173.76 + /// Gets or sets the end value.
173.77 + /// </summary>
173.78 + public double End { get; set; }
173.79 +
173.80 + /// <summary>
173.81 + /// Gets or sets the start value.
173.82 + /// </summary>
173.83 + public double Start { get; set; }
173.84 +
173.85 + /// <summary>
173.86 + /// Gets or sets the title.
173.87 + /// </summary>
173.88 + public string Title { get; set; }
173.89 +
173.90 + /// <summary>
173.91 + /// Returns c# code that generates this instance.
173.92 + /// </summary>
173.93 + /// <returns>
173.94 + /// C# code.
173.95 + /// </returns>
173.96 + public string ToCode()
173.97 + {
173.98 + if (this.Color != null)
173.99 + {
173.100 + return CodeGenerator.FormatConstructor(
173.101 + this.GetType(), "{0},{1},{2},{3}", this.Start, this.End, this.Title, this.Color.ToCode());
173.102 + }
173.103 +
173.104 + if (this.Title != null)
173.105 + {
173.106 + return CodeGenerator.FormatConstructor(this.GetType(), "{0},{1},{2}", this.Start, this.End, this.Title);
173.107 + }
173.108 +
173.109 + return CodeGenerator.FormatConstructor(this.GetType(), "{0},{1}", this.Start, this.End);
173.110 + }
173.111 +
173.112 + }
173.113 +}
173.114 \ No newline at end of file
174.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
174.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/IntervalBarSeries.cs Sat Jun 08 16:53:22 2013 +0000
174.3 @@ -0,0 +1,515 @@
174.4 +// --------------------------------------------------------------------------------------------------------------------
174.5 +// <copyright file="IntervalBarSeries.cs" company="OxyPlot">
174.6 +// The MIT License (MIT)
174.7 +//
174.8 +// Copyright (c) 2012 Oystein Bjorke
174.9 +//
174.10 +// Permission is hereby granted, free of charge, to any person obtaining a
174.11 +// copy of this software and associated documentation files (the
174.12 +// "Software"), to deal in the Software without restriction, including
174.13 +// without limitation the rights to use, copy, modify, merge, publish,
174.14 +// distribute, sublicense, and/or sell copies of the Software, and to
174.15 +// permit persons to whom the Software is furnished to do so, subject to
174.16 +// the following conditions:
174.17 +//
174.18 +// The above copyright notice and this permission notice shall be included
174.19 +// in all copies or substantial portions of the Software.
174.20 +//
174.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
174.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
174.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
174.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
174.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
174.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
174.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
174.28 +// </copyright>
174.29 +// <summary>
174.30 +// Represents a series for bar charts defined by to/from values.
174.31 +// </summary>
174.32 +// --------------------------------------------------------------------------------------------------------------------
174.33 +namespace OxyPlot.Series
174.34 +{
174.35 + using System;
174.36 + using System.Collections.Generic;
174.37 + using System.Linq;
174.38 +
174.39 + using OxyPlot.Axes;
174.40 +
174.41 + /// <summary>
174.42 + /// Represents a series for bar charts defined by to/from values.
174.43 + /// </summary>
174.44 + public class IntervalBarSeries : CategorizedSeries, IStackableSeries
174.45 + {
174.46 + /// <summary>
174.47 + /// The default fill color.
174.48 + /// </summary>
174.49 + private OxyColor defaultFillColor;
174.50 +
174.51 + /// <summary>
174.52 + /// Initializes a new instance of the <see cref="IntervalBarSeries"/> class.
174.53 + /// </summary>
174.54 + public IntervalBarSeries()
174.55 + {
174.56 + this.Items = new List<IntervalBarItem>();
174.57 +
174.58 + this.StrokeColor = OxyColors.Black;
174.59 + this.StrokeThickness = 1;
174.60 + this.BarWidth = 1;
174.61 +
174.62 + this.TrackerFormatString = "{0}";
174.63 + this.LabelMargin = 4;
174.64 +
174.65 + this.LabelFormatString = "{2}"; // title
174.66 +
174.67 + // this.LabelFormatString = "{0}-{1}"; // Minimum-Maximum
174.68 + }
174.69 +
174.70 + /// <summary>
174.71 + /// Gets or sets the width of the bars (as a fraction of the available width). The default value is 0.5 (50%)
174.72 + /// </summary>
174.73 + /// <value>
174.74 + /// The width of the bars.
174.75 + /// </value>
174.76 + public double BarWidth { get; set; }
174.77 +
174.78 + /// <summary>
174.79 + /// Gets or sets the default color of the interior of the Maximum bars.
174.80 + /// </summary>
174.81 + /// <value>
174.82 + /// The color.
174.83 + /// </value>
174.84 + public OxyColor FillColor { get; set; }
174.85 +
174.86 + /// <summary>
174.87 + /// Gets the actual fill color.
174.88 + /// </summary>
174.89 + /// <value>The actual color.</value>
174.90 + public OxyColor ActualFillColor
174.91 + {
174.92 + get { return this.FillColor ?? this.defaultFillColor; }
174.93 + }
174.94 +
174.95 + /// <summary>
174.96 + /// Gets a value indicating whether IsStacked.
174.97 + /// </summary>
174.98 + public bool IsStacked
174.99 + {
174.100 + get
174.101 + {
174.102 + return true;
174.103 + }
174.104 + }
174.105 +
174.106 + /// <summary>
174.107 + /// Gets the range bar items.
174.108 + /// </summary>
174.109 + public IList<IntervalBarItem> Items { get; private set; }
174.110 +
174.111 + /// <summary>
174.112 + /// Gets or sets the label color.
174.113 + /// </summary>
174.114 + public OxyColor LabelColor { get; set; }
174.115 +
174.116 + /// <summary>
174.117 + /// Gets or sets the label field.
174.118 + /// </summary>
174.119 + public string LabelField { get; set; }
174.120 +
174.121 + /// <summary>
174.122 + /// Gets or sets the format string for the maximum labels.
174.123 + /// </summary>
174.124 + public string LabelFormatString { get; set; }
174.125 +
174.126 + /// <summary>
174.127 + /// Gets or sets the label margins.
174.128 + /// </summary>
174.129 + public double LabelMargin { get; set; }
174.130 +
174.131 + /// <summary>
174.132 + /// Gets or sets the maximum value field.
174.133 + /// </summary>
174.134 + public string MaximumField { get; set; }
174.135 +
174.136 + /// <summary>
174.137 + /// Gets or sets the minimum value field.
174.138 + /// </summary>
174.139 + public string MinimumField { get; set; }
174.140 +
174.141 + /// <summary>
174.142 + /// Gets StackGroup.
174.143 + /// </summary>
174.144 + public string StackGroup
174.145 + {
174.146 + get
174.147 + {
174.148 + return string.Empty;
174.149 + }
174.150 + }
174.151 +
174.152 + /// <summary>
174.153 + /// Gets or sets the color of the border around the bars.
174.154 + /// </summary>
174.155 + /// <value>
174.156 + /// The color of the stroke.
174.157 + /// </value>
174.158 + public OxyColor StrokeColor { get; set; }
174.159 +
174.160 + /// <summary>
174.161 + /// Gets or sets the thickness of the bar border strokes.
174.162 + /// </summary>
174.163 + /// <value>
174.164 + /// The stroke thickness.
174.165 + /// </value>
174.166 + public double StrokeThickness { get; set; }
174.167 +
174.168 + /// <summary>
174.169 + /// Gets or sets the actual rectangles for the maximum bars.
174.170 + /// </summary>
174.171 + protected internal IList<OxyRect> ActualBarRectangles { get; set; }
174.172 +
174.173 + /// <summary>
174.174 + /// Gets or sets the valid items
174.175 + /// </summary>
174.176 + protected internal IList<IntervalBarItem> ValidItems { get; set; }
174.177 +
174.178 + /// <summary>
174.179 + /// Gets or sets the dictionary which stores the index-inversion for the valid items
174.180 + /// </summary>
174.181 + protected internal Dictionary<int, int> ValidItemsIndexInversion { get; set; }
174.182 +
174.183 + /// <summary>
174.184 + /// Gets the point in the dataset that is nearest the specified point.
174.185 + /// </summary>
174.186 + /// <param name="point">
174.187 + /// The point.
174.188 + /// </param>
174.189 + /// <param name="interpolate">
174.190 + /// The interpolate.
174.191 + /// </param>
174.192 + /// <returns>
174.193 + /// A TrackerHitResult for the current hit.
174.194 + /// </returns>
174.195 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
174.196 + {
174.197 + for (int i = 0; i < this.ActualBarRectangles.Count; i++)
174.198 + {
174.199 + var r = this.ActualBarRectangles[i];
174.200 + if (r.Contains(point))
174.201 + {
174.202 + var item = (IntervalBarItem)this.GetItem(this.ValidItemsIndexInversion[i]);
174.203 + var categoryIndex = item.GetCategoryIndex(i);
174.204 + double value = (this.ValidItems[i].Start + this.ValidItems[i].End) / 2;
174.205 + var dp = new DataPoint(categoryIndex, value);
174.206 + var text = StringHelper.Format(
174.207 + this.ActualCulture,
174.208 + this.TrackerFormatString,
174.209 + item,
174.210 + this.Items[i].Start,
174.211 + this.Items[i].End,
174.212 + this.Items[i].Title);
174.213 + return new TrackerHitResult(this, dp, point, item, i, text);
174.214 + }
174.215 + }
174.216 +
174.217 + return null;
174.218 + }
174.219 +
174.220 + /// <summary>
174.221 + /// Checks if the specified value is valid.
174.222 + /// </summary>
174.223 + /// <param name="v">
174.224 + /// The value.
174.225 + /// </param>
174.226 + /// <param name="yaxis">
174.227 + /// The y axis.
174.228 + /// </param>
174.229 + /// <returns>
174.230 + /// True if the value is valid.
174.231 + /// </returns>
174.232 + public virtual bool IsValidPoint(double v, Axis yaxis)
174.233 + {
174.234 + return !double.IsNaN(v) && !double.IsInfinity(v);
174.235 + }
174.236 +
174.237 + /// <summary>
174.238 + /// Renders the Series on the specified rendering context.
174.239 + /// </summary>
174.240 + /// <param name="rc">
174.241 + /// The rendering context.
174.242 + /// </param>
174.243 + /// <param name="model">
174.244 + /// The model.
174.245 + /// </param>
174.246 + public override void Render(IRenderContext rc, PlotModel model)
174.247 + {
174.248 + this.ActualBarRectangles = new List<OxyRect>();
174.249 +
174.250 + if (this.ValidItems.Count == 0)
174.251 + {
174.252 + return;
174.253 + }
174.254 +
174.255 + var clippingRect = this.GetClippingRect();
174.256 + var categoryAxis = this.GetCategoryAxis();
174.257 +
174.258 + var actualBarWidth = this.GetActualBarWidth();
174.259 + var stackIndex = categoryAxis.StackIndexMapping[this.StackGroup];
174.260 +
174.261 + for (var i = 0; i < this.ValidItems.Count; i++)
174.262 + {
174.263 + var item = this.ValidItems[i];
174.264 +
174.265 + var categoryIndex = item.GetCategoryIndex(i);
174.266 + double categoryValue = categoryAxis.GetCategoryValue(categoryIndex, stackIndex, actualBarWidth);
174.267 +
174.268 + var p0 = this.Transform(item.Start, categoryValue);
174.269 + var p1 = this.Transform(item.End, categoryValue + actualBarWidth);
174.270 +
174.271 + var rectangle = OxyRect.Create(p0.X, p0.Y, p1.X, p1.Y);
174.272 +
174.273 + this.ActualBarRectangles.Add(rectangle);
174.274 +
174.275 + rc.DrawClippedRectangleAsPolygon(
174.276 + rectangle,
174.277 + clippingRect,
174.278 + this.GetSelectableFillColor(item.Color ?? this.ActualFillColor),
174.279 + this.StrokeColor,
174.280 + this.StrokeThickness);
174.281 +
174.282 + if (this.LabelFormatString != null)
174.283 + {
174.284 + var s = StringHelper.Format(
174.285 + this.ActualCulture, this.LabelFormatString, this.GetItem(i), item.Start, item.End, item.Title);
174.286 +
174.287 + var pt = new ScreenPoint(
174.288 + (rectangle.Left + rectangle.Right) / 2, (rectangle.Top + rectangle.Bottom) / 2);
174.289 +
174.290 + rc.DrawClippedText(
174.291 + clippingRect,
174.292 + pt,
174.293 + s,
174.294 + this.ActualTextColor,
174.295 + this.ActualFont,
174.296 + this.ActualFontSize,
174.297 + this.ActualFontWeight,
174.298 + 0,
174.299 + HorizontalAlignment.Center,
174.300 + VerticalAlignment.Middle);
174.301 + }
174.302 + }
174.303 + }
174.304 +
174.305 + /// <summary>
174.306 + /// Renders the legend symbol on the specified rendering context.
174.307 + /// </summary>
174.308 + /// <param name="rc">
174.309 + /// The rendering context.
174.310 + /// </param>
174.311 + /// <param name="legendBox">
174.312 + /// The legend rectangle.
174.313 + /// </param>
174.314 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
174.315 + {
174.316 + double xmid = (legendBox.Left + legendBox.Right) / 2;
174.317 + double ymid = (legendBox.Top + legendBox.Bottom) / 2;
174.318 + double height = (legendBox.Bottom - legendBox.Top) * 0.8;
174.319 + double width = height;
174.320 + rc.DrawRectangleAsPolygon(
174.321 + new OxyRect(xmid - (0.5 * width), ymid - (0.5 * height), width, height),
174.322 + this.GetSelectableFillColor(this.ActualFillColor),
174.323 + this.StrokeColor,
174.324 + this.StrokeThickness);
174.325 + }
174.326 +
174.327 + /// <summary>
174.328 + /// Gets or sets the width/height of the columns/bars (as a fraction of the available space).
174.329 + /// </summary>
174.330 + /// <returns>
174.331 + /// The fractional width.
174.332 + /// </returns>
174.333 + /// <value>
174.334 + /// The width of the bars.
174.335 + /// </value>
174.336 + /// <remarks>
174.337 + /// The available space will be determined by the GapWidth of the CategoryAxis used by this series.
174.338 + /// </remarks>
174.339 + internal override double GetBarWidth()
174.340 + {
174.341 + return this.BarWidth;
174.342 + }
174.343 +
174.344 + /// <summary>
174.345 + /// Gets the items of this series.
174.346 + /// </summary>
174.347 + /// <returns>
174.348 + /// The items.
174.349 + /// </returns>
174.350 + protected internal override IList<CategorizedItem> GetItems()
174.351 + {
174.352 + return this.Items.Cast<CategorizedItem>().ToList();
174.353 + }
174.354 +
174.355 + /// <summary>
174.356 + /// Check if the data series is using the specified axis.
174.357 + /// </summary>
174.358 + /// <param name="axis">
174.359 + /// An axis which should be checked if used
174.360 + /// </param>
174.361 + /// <returns>
174.362 + /// True if the axis is in use.
174.363 + /// </returns>
174.364 + protected internal override bool IsUsing(Axis axis)
174.365 + {
174.366 + return this.XAxis == axis || this.YAxis == axis;
174.367 + }
174.368 +
174.369 + /// <summary>
174.370 + /// The set default values.
174.371 + /// </summary>
174.372 + /// <param name="model">
174.373 + /// The model.
174.374 + /// </param>
174.375 + protected internal override void SetDefaultValues(PlotModel model)
174.376 + {
174.377 + if (this.FillColor == null)
174.378 + {
174.379 + this.defaultFillColor = model.GetDefaultColor();
174.380 + }
174.381 + }
174.382 +
174.383 + /// <summary>
174.384 + /// Updates the axis maximum and minimum values.
174.385 + /// </summary>
174.386 + protected internal override void UpdateAxisMaxMin()
174.387 + {
174.388 + this.XAxis.Include(this.MinX);
174.389 + this.XAxis.Include(this.MaxX);
174.390 + }
174.391 +
174.392 + /// <summary>
174.393 + /// Updates the data.
174.394 + /// </summary>
174.395 + protected internal override void UpdateData()
174.396 + {
174.397 + if (this.ItemsSource != null)
174.398 + {
174.399 + this.Items.Clear();
174.400 +
174.401 + var filler = new ListFiller<IntervalBarItem>();
174.402 + filler.Add(this.MinimumField, (item, value) => item.Start = Convert.ToDouble(value));
174.403 + filler.Add(this.MaximumField, (item, value) => item.End = Convert.ToDouble(value));
174.404 + filler.FillT(this.Items, this.ItemsSource);
174.405 + }
174.406 + }
174.407 +
174.408 + /// <summary>
174.409 + /// Updates the maximum/minimum value on the value axis from the bar values.
174.410 + /// </summary>
174.411 + protected internal override void UpdateMaxMin()
174.412 + {
174.413 + base.UpdateMaxMin();
174.414 +
174.415 + if (this.ValidItems == null || this.ValidItems.Count == 0)
174.416 + {
174.417 + return;
174.418 + }
174.419 +
174.420 + double minValue = double.MaxValue;
174.421 + double maxValue = double.MinValue;
174.422 +
174.423 + foreach (var item in this.ValidItems)
174.424 + {
174.425 + minValue = Math.Min(minValue, item.Start);
174.426 + minValue = Math.Min(minValue, item.End);
174.427 + maxValue = Math.Max(maxValue, item.Start);
174.428 + maxValue = Math.Max(maxValue, item.End);
174.429 + }
174.430 +
174.431 + this.MinX = minValue;
174.432 + this.MaxX = maxValue;
174.433 + }
174.434 +
174.435 + /// <summary>
174.436 + /// Updates the valid items
174.437 + /// </summary>
174.438 + protected internal override void UpdateValidData()
174.439 + {
174.440 + this.ValidItems = new List<IntervalBarItem>();
174.441 + this.ValidItemsIndexInversion = new Dictionary<int, int>();
174.442 + var valueAxis = this.GetValueAxis();
174.443 +
174.444 + for (var i = 0; i < this.Items.Count; i++)
174.445 + {
174.446 + var item = this.Items[i];
174.447 + if (valueAxis.IsValidValue(item.Start) && valueAxis.IsValidValue(item.End))
174.448 + {
174.449 + this.ValidItemsIndexInversion.Add(this.ValidItems.Count, i);
174.450 + this.ValidItems.Add(item);
174.451 + }
174.452 + }
174.453 + }
174.454 +
174.455 + /// <summary>
174.456 + /// Gets the actual width/height of the items of this series.
174.457 + /// </summary>
174.458 + /// <returns>
174.459 + /// The width or height.
174.460 + /// </returns>
174.461 + /// <remarks>
174.462 + /// The actual width is also influenced by the GapWidth of the CategoryAxis used by this series.
174.463 + /// </remarks>
174.464 + protected override double GetActualBarWidth()
174.465 + {
174.466 + var categoryAxis = this.GetCategoryAxis();
174.467 + return this.BarWidth / (1 + categoryAxis.GapWidth) / categoryAxis.MaxWidth;
174.468 + }
174.469 +
174.470 + /// <summary>
174.471 + /// Gets the category axis.
174.472 + /// </summary>
174.473 + /// <returns>
174.474 + /// The category axis.
174.475 + /// </returns>
174.476 + protected override CategoryAxis GetCategoryAxis()
174.477 + {
174.478 + var categoryAxis = this.YAxis as CategoryAxis;
174.479 + if (categoryAxis == null)
174.480 + {
174.481 + throw new InvalidOperationException("No category axis defined.");
174.482 + }
174.483 +
174.484 + return categoryAxis;
174.485 + }
174.486 +
174.487 + /// <summary>
174.488 + /// Gets the item at the specified index.
174.489 + /// </summary>
174.490 + /// <param name="i">
174.491 + /// The index of the item.
174.492 + /// </param>
174.493 + /// <returns>
174.494 + /// The item of the index.
174.495 + /// </returns>
174.496 + protected override object GetItem(int i)
174.497 + {
174.498 + if (this.ItemsSource != null || this.Items == null || this.Items.Count == 0)
174.499 + {
174.500 + return base.GetItem(i);
174.501 + }
174.502 +
174.503 + return this.Items[i];
174.504 + }
174.505 +
174.506 + /// <summary>
174.507 + /// Gets the value axis.
174.508 + /// </summary>
174.509 + /// <returns>
174.510 + /// The value axis.
174.511 + /// </returns>
174.512 + private Axis GetValueAxis()
174.513 + {
174.514 + return this.XAxis;
174.515 + }
174.516 +
174.517 + }
174.518 +}
174.519 \ No newline at end of file
175.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
175.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/LabelPlacement.cs Sat Jun 08 16:53:22 2013 +0000
175.3 @@ -0,0 +1,57 @@
175.4 +// --------------------------------------------------------------------------------------------------------------------
175.5 +// <copyright file="LabelPlacement.cs" company="OxyPlot">
175.6 +// The MIT License (MIT)
175.7 +//
175.8 +// Copyright (c) 2012 Oystein Bjorke
175.9 +//
175.10 +// Permission is hereby granted, free of charge, to any person obtaining a
175.11 +// copy of this software and associated documentation files (the
175.12 +// "Software"), to deal in the Software without restriction, including
175.13 +// without limitation the rights to use, copy, modify, merge, publish,
175.14 +// distribute, sublicense, and/or sell copies of the Software, and to
175.15 +// permit persons to whom the Software is furnished to do so, subject to
175.16 +// the following conditions:
175.17 +//
175.18 +// The above copyright notice and this permission notice shall be included
175.19 +// in all copies or substantial portions of the Software.
175.20 +//
175.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
175.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
175.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
175.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
175.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
175.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
175.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
175.28 +// </copyright>
175.29 +// <summary>
175.30 +// Placement of the labels.
175.31 +// </summary>
175.32 +// --------------------------------------------------------------------------------------------------------------------
175.33 +namespace OxyPlot.Series
175.34 +{
175.35 + /// <summary>
175.36 + /// Placement of the labels.
175.37 + /// </summary>
175.38 + public enum LabelPlacement
175.39 + {
175.40 + /// <summary>
175.41 + /// Placed outside the bar.
175.42 + /// </summary>
175.43 + Outside,
175.44 +
175.45 + /// <summary>
175.46 + /// Placed inside the bar.
175.47 + /// </summary>
175.48 + Inside,
175.49 +
175.50 + /// <summary>
175.51 + /// Placed inside in the middle/center of the bar.
175.52 + /// </summary>
175.53 + Middle,
175.54 +
175.55 + /// <summary>
175.56 + /// Placed inside at the base of the bar.
175.57 + /// </summary>
175.58 + Base
175.59 + }
175.60 +}
175.61 \ No newline at end of file
176.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
176.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/RectangleBarItem.cs Sat Jun 08 16:53:22 2013 +0000
176.3 @@ -0,0 +1,137 @@
176.4 +// --------------------------------------------------------------------------------------------------------------------
176.5 +// <copyright file="RectangleBarItem.cs" company="OxyPlot">
176.6 +// The MIT License (MIT)
176.7 +//
176.8 +// Copyright (c) 2012 Oystein Bjorke
176.9 +//
176.10 +// Permission is hereby granted, free of charge, to any person obtaining a
176.11 +// copy of this software and associated documentation files (the
176.12 +// "Software"), to deal in the Software without restriction, including
176.13 +// without limitation the rights to use, copy, modify, merge, publish,
176.14 +// distribute, sublicense, and/or sell copies of the Software, and to
176.15 +// permit persons to whom the Software is furnished to do so, subject to
176.16 +// the following conditions:
176.17 +//
176.18 +// The above copyright notice and this permission notice shall be included
176.19 +// in all copies or substantial portions of the Software.
176.20 +//
176.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
176.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
176.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
176.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
176.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
176.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
176.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
176.28 +// </copyright>
176.29 +// <summary>
176.30 +// Represents a rectangle item in a RectangleBarSeries.
176.31 +// </summary>
176.32 +// --------------------------------------------------------------------------------------------------------------------
176.33 +namespace OxyPlot.Series
176.34 +{
176.35 + /// <summary>
176.36 + /// Represents a rectangle item in a RectangleBarSeries.
176.37 + /// </summary>
176.38 + public class RectangleBarItem : ICodeGenerating
176.39 + {
176.40 + /// <summary>
176.41 + /// Initializes a new instance of the <see cref="RectangleBarItem"/> class.
176.42 + /// </summary>
176.43 + public RectangleBarItem()
176.44 + {
176.45 + }
176.46 +
176.47 + /// <summary>
176.48 + /// Initializes a new instance of the <see cref="RectangleBarItem"/> class.
176.49 + /// </summary>
176.50 + /// <param name="x0">
176.51 + /// The x0.
176.52 + /// </param>
176.53 + /// <param name="y0">
176.54 + /// The y0.
176.55 + /// </param>
176.56 + /// <param name="x1">
176.57 + /// The x1.
176.58 + /// </param>
176.59 + /// <param name="y1">
176.60 + /// The y1.
176.61 + /// </param>
176.62 + /// <param name="title">
176.63 + /// The title.
176.64 + /// </param>
176.65 + /// <param name="color">
176.66 + /// The color.
176.67 + /// </param>
176.68 + public RectangleBarItem(double x0, double y0, double x1, double y1, string title = null, OxyColor color = null)
176.69 + {
176.70 + this.X0 = x0;
176.71 + this.Y0 = y0;
176.72 + this.X1 = x1;
176.73 + this.Y1 = y1;
176.74 + this.Title = title;
176.75 + this.Color = color;
176.76 + }
176.77 +
176.78 + /// <summary>
176.79 + /// Gets or sets the color.
176.80 + /// </summary>
176.81 + public OxyColor Color { get; set; }
176.82 +
176.83 + /// <summary>
176.84 + /// Gets or sets the title.
176.85 + /// </summary>
176.86 + public string Title { get; set; }
176.87 +
176.88 + /// <summary>
176.89 + /// Gets or sets the x0 coordinate.
176.90 + /// </summary>
176.91 + public double X0 { get; set; }
176.92 +
176.93 + /// <summary>
176.94 + /// Gets or sets the x1 coordinate.
176.95 + /// </summary>
176.96 + public double X1 { get; set; }
176.97 +
176.98 + /// <summary>
176.99 + /// Gets or sets the y0 coordinate.
176.100 + /// </summary>
176.101 + public double Y0 { get; set; }
176.102 +
176.103 + /// <summary>
176.104 + /// Gets or sets the y1 coordinate.
176.105 + /// </summary>
176.106 + public double Y1 { get; set; }
176.107 +
176.108 + /// <summary>
176.109 + /// Returns c# code that generates this instance.
176.110 + /// </summary>
176.111 + /// <returns>
176.112 + /// C# code.
176.113 + /// </returns>
176.114 + public string ToCode()
176.115 + {
176.116 + if (this.Color != null)
176.117 + {
176.118 + return CodeGenerator.FormatConstructor(
176.119 + this.GetType(),
176.120 + "{0},{1},{2},{3},{4},{5}",
176.121 + this.X0,
176.122 + this.Y0,
176.123 + this.X1,
176.124 + this.Y1,
176.125 + this.Title,
176.126 + this.Color.ToCode());
176.127 + }
176.128 +
176.129 + if (this.Title != null)
176.130 + {
176.131 + return CodeGenerator.FormatConstructor(
176.132 + this.GetType(), "{0},{1},{2},{3},{4}", this.X0, this.Y0, this.X1, this.Y1, this.Title);
176.133 + }
176.134 +
176.135 + return CodeGenerator.FormatConstructor(
176.136 + this.GetType(), "{0},{1},{2},{3}", this.X0, this.Y0, this.X1, this.Y1);
176.137 + }
176.138 +
176.139 + }
176.140 +}
176.141 \ No newline at end of file
177.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
177.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/RectangleBarSeries.cs Sat Jun 08 16:53:22 2013 +0000
177.3 @@ -0,0 +1,337 @@
177.4 +// --------------------------------------------------------------------------------------------------------------------
177.5 +// <copyright file="RectangleBarSeries.cs" company="OxyPlot">
177.6 +// The MIT License (MIT)
177.7 +//
177.8 +// Copyright (c) 2012 Oystein Bjorke
177.9 +//
177.10 +// Permission is hereby granted, free of charge, to any person obtaining a
177.11 +// copy of this software and associated documentation files (the
177.12 +// "Software"), to deal in the Software without restriction, including
177.13 +// without limitation the rights to use, copy, modify, merge, publish,
177.14 +// distribute, sublicense, and/or sell copies of the Software, and to
177.15 +// permit persons to whom the Software is furnished to do so, subject to
177.16 +// the following conditions:
177.17 +//
177.18 +// The above copyright notice and this permission notice shall be included
177.19 +// in all copies or substantial portions of the Software.
177.20 +//
177.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
177.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
177.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
177.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
177.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
177.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
177.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
177.28 +// </copyright>
177.29 +// <summary>
177.30 +// Represents a series for bar charts where the bars are defined by rectangles.
177.31 +// </summary>
177.32 +// --------------------------------------------------------------------------------------------------------------------
177.33 +namespace OxyPlot.Series
177.34 +{
177.35 + using System;
177.36 + using System.Collections.Generic;
177.37 +
177.38 + /// <summary>
177.39 + /// Represents a series for bar charts where the bars are defined by rectangles.
177.40 + /// </summary>
177.41 + public class RectangleBarSeries : XYAxisSeries
177.42 + {
177.43 + /// <summary>
177.44 + /// The default fill color.
177.45 + /// </summary>
177.46 + private OxyColor defaultFillColor;
177.47 +
177.48 + /// <summary>
177.49 + /// Initializes a new instance of the <see cref="RectangleBarSeries"/> class.
177.50 + /// </summary>
177.51 + public RectangleBarSeries()
177.52 + {
177.53 + this.Items = new List<RectangleBarItem>();
177.54 +
177.55 + this.StrokeColor = OxyColors.Black;
177.56 + this.StrokeThickness = 1;
177.57 +
177.58 + this.TrackerFormatString = "{0}";
177.59 +
177.60 + this.LabelFormatString = "{4}"; // title
177.61 +
177.62 + // this.LabelFormatString = "{0}-{1},{2}-{3}"; // X0-X1,Y0-Y1
177.63 + }
177.64 +
177.65 + /// <summary>
177.66 + /// Gets or sets the default color of the interior of the rectangles.
177.67 + /// </summary>
177.68 + /// <value>
177.69 + /// The color.
177.70 + /// </value>
177.71 + public OxyColor FillColor { get; set; }
177.72 +
177.73 + /// <summary>
177.74 + /// Gets the actual fill color.
177.75 + /// </summary>
177.76 + /// <value>The actual color.</value>
177.77 + public OxyColor ActualFillColor
177.78 + {
177.79 + get { return this.FillColor ?? this.defaultFillColor; }
177.80 + }
177.81 +
177.82 + /// <summary>
177.83 + /// Gets the rectangle bar items.
177.84 + /// </summary>
177.85 + public IList<RectangleBarItem> Items { get; private set; }
177.86 +
177.87 + /// <summary>
177.88 + /// Gets or sets the label color.
177.89 + /// </summary>
177.90 + public OxyColor LabelColor { get; set; }
177.91 +
177.92 + /// <summary>
177.93 + /// Gets or sets the format string for the labels.
177.94 + /// </summary>
177.95 + public string LabelFormatString { get; set; }
177.96 +
177.97 + /// <summary>
177.98 + /// Gets or sets the color of the border around the rectangles.
177.99 + /// </summary>
177.100 + /// <value>
177.101 + /// The color of the stroke.
177.102 + /// </value>
177.103 + public OxyColor StrokeColor { get; set; }
177.104 +
177.105 + /// <summary>
177.106 + /// Gets or sets the thickness of the border around the rectangles.
177.107 + /// </summary>
177.108 + /// <value>
177.109 + /// The stroke thickness.
177.110 + /// </value>
177.111 + public double StrokeThickness { get; set; }
177.112 +
177.113 + /// <summary>
177.114 + /// Gets or sets the actual rectangles for the rectangles.
177.115 + /// </summary>
177.116 + internal IList<OxyRect> ActualBarRectangles { get; set; }
177.117 +
177.118 + /// <summary>
177.119 + /// Gets the point in the dataset that is nearest the specified point.
177.120 + /// </summary>
177.121 + /// <param name="point">
177.122 + /// The point.
177.123 + /// </param>
177.124 + /// <param name="interpolate">
177.125 + /// Specifies whether to interpolate or not.
177.126 + /// </param>
177.127 + /// <returns>
177.128 + /// A <see cref="TrackerHitResult"/> for the current hit.
177.129 + /// </returns>
177.130 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
177.131 + {
177.132 + if (this.ActualBarRectangles == null)
177.133 + {
177.134 + return null;
177.135 + }
177.136 +
177.137 + for (int i = 0; i < this.ActualBarRectangles.Count; i++)
177.138 + {
177.139 + var r = this.ActualBarRectangles[i];
177.140 + if (r.Contains(point))
177.141 + {
177.142 + double value = (this.Items[i].Y0 + this.Items[i].Y1) / 2;
177.143 + var sp = point;
177.144 + var dp = new DataPoint(i, value);
177.145 + var item = this.GetItem(i);
177.146 + var text = StringHelper.Format(
177.147 + this.ActualCulture,
177.148 + this.TrackerFormatString,
177.149 + item,
177.150 + this.Items[i].X0,
177.151 + this.Items[i].X1,
177.152 + this.Items[i].Y0,
177.153 + this.Items[i].Y1,
177.154 + this.Items[i].Title);
177.155 + return new TrackerHitResult(this, dp, sp, item, i, text);
177.156 + }
177.157 + }
177.158 +
177.159 + return null;
177.160 + }
177.161 +
177.162 + /// <summary>
177.163 + /// Checks if the specified value is valid.
177.164 + /// </summary>
177.165 + /// <param name="v">
177.166 + /// The value.
177.167 + /// </param>
177.168 + /// <returns>
177.169 + /// True if the value is valid.
177.170 + /// </returns>
177.171 + protected virtual bool IsValid(double v)
177.172 + {
177.173 + return !double.IsNaN(v) && !double.IsInfinity(v);
177.174 + }
177.175 +
177.176 + /// <summary>
177.177 + /// Renders the Series on the specified rendering context.
177.178 + /// </summary>
177.179 + /// <param name="rc">
177.180 + /// The rendering context.
177.181 + /// </param>
177.182 + /// <param name="model">
177.183 + /// The model.
177.184 + /// </param>
177.185 + public override void Render(IRenderContext rc, PlotModel model)
177.186 + {
177.187 + if (this.Items.Count == 0)
177.188 + {
177.189 + return;
177.190 + }
177.191 +
177.192 + var clippingRect = this.GetClippingRect();
177.193 +
177.194 + int i = 0;
177.195 +
177.196 + this.ActualBarRectangles = new List<OxyRect>();
177.197 +
177.198 + foreach (var item in this.Items)
177.199 + {
177.200 + if (!this.IsValid(item.X0) || !this.IsValid(item.X1)
177.201 + || !this.IsValid(item.Y0) || !this.IsValid(item.Y1))
177.202 + {
177.203 + continue;
177.204 + }
177.205 +
177.206 + var p0 = this.Transform(item.X0, item.Y0);
177.207 + var p1 = this.Transform(item.X1, item.Y1);
177.208 +
177.209 + var rectangle = OxyRect.Create(p0.X, p0.Y, p1.X, p1.Y);
177.210 +
177.211 + this.ActualBarRectangles.Add(rectangle);
177.212 +
177.213 + rc.DrawClippedRectangleAsPolygon(
177.214 + rectangle,
177.215 + clippingRect,
177.216 + this.GetSelectableFillColor(item.Color ?? this.ActualFillColor),
177.217 + this.StrokeColor,
177.218 + this.StrokeThickness);
177.219 +
177.220 + if (this.LabelFormatString != null)
177.221 + {
177.222 + var s = StringHelper.Format(
177.223 + this.ActualCulture,
177.224 + this.LabelFormatString,
177.225 + this.GetItem(i),
177.226 + item.X0,
177.227 + item.X1,
177.228 + item.Y0,
177.229 + item.Y1,
177.230 + item.Title);
177.231 +
177.232 + var pt = new ScreenPoint(
177.233 + (rectangle.Left + rectangle.Right) / 2, (rectangle.Top + rectangle.Bottom) / 2);
177.234 +
177.235 + rc.DrawClippedText(
177.236 + clippingRect,
177.237 + pt,
177.238 + s,
177.239 + this.ActualTextColor,
177.240 + this.ActualFont,
177.241 + this.ActualFontSize,
177.242 + this.ActualFontWeight,
177.243 + 0,
177.244 + HorizontalAlignment.Center,
177.245 + VerticalAlignment.Middle);
177.246 + }
177.247 +
177.248 + i++;
177.249 + }
177.250 + }
177.251 +
177.252 + /// <summary>
177.253 + /// Renders the legend symbol on the specified rendering context.
177.254 + /// </summary>
177.255 + /// <param name="rc">
177.256 + /// The rendering context.
177.257 + /// </param>
177.258 + /// <param name="legendBox">
177.259 + /// The legend rectangle.
177.260 + /// </param>
177.261 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
177.262 + {
177.263 + double xmid = (legendBox.Left + legendBox.Right) / 2;
177.264 + double ymid = (legendBox.Top + legendBox.Bottom) / 2;
177.265 + double height = (legendBox.Bottom - legendBox.Top) * 0.8;
177.266 + double width = height;
177.267 + rc.DrawRectangleAsPolygon(
177.268 + new OxyRect(xmid - (0.5 * width), ymid - (0.5 * height), width, height),
177.269 + this.GetSelectableFillColor(this.ActualFillColor),
177.270 + this.StrokeColor,
177.271 + this.StrokeThickness);
177.272 + }
177.273 +
177.274 + /// <summary>
177.275 + /// Sets the default values.
177.276 + /// </summary>
177.277 + /// <param name="model">
177.278 + /// The model.
177.279 + /// </param>
177.280 + protected internal override void SetDefaultValues(PlotModel model)
177.281 + {
177.282 + if (this.FillColor == null)
177.283 + {
177.284 + this.defaultFillColor = model.GetDefaultColor();
177.285 + }
177.286 + }
177.287 +
177.288 + /// <summary>
177.289 + /// Updates the data.
177.290 + /// </summary>
177.291 + protected internal override void UpdateData()
177.292 + {
177.293 + if (this.ItemsSource == null)
177.294 + {
177.295 + return;
177.296 + }
177.297 +
177.298 + this.Items.Clear();
177.299 +
177.300 + // ReflectionHelper.FillList(
177.301 + // this.ItemsSource,
177.302 + // this.Items,
177.303 + // new[] { this.MinimumField, this.MaximumField },
177.304 + // (item, value) => item.Minimum = Convert.ToDouble(value),
177.305 + // (item, value) => item.Maximum = Convert.ToDouble(value));
177.306 + throw new NotImplementedException();
177.307 + }
177.308 +
177.309 + /// <summary>
177.310 + /// Updates the maximum/minimum value on the value axis from the bar values.
177.311 + /// </summary>
177.312 + protected internal override void UpdateMaxMin()
177.313 + {
177.314 + base.UpdateMaxMin();
177.315 +
177.316 + if (this.Items == null || this.Items.Count == 0)
177.317 + {
177.318 + return;
177.319 + }
177.320 +
177.321 + double minValueX = double.MaxValue;
177.322 + double maxValueX = double.MinValue;
177.323 + double minValueY = double.MaxValue;
177.324 + double maxValueY = double.MinValue;
177.325 +
177.326 + foreach (var item in this.Items)
177.327 + {
177.328 + minValueX = Math.Min(minValueX, Math.Min(item.X0, item.X1));
177.329 + maxValueX = Math.Max(maxValueX, Math.Max(item.X1, item.X0));
177.330 + minValueY = Math.Min(minValueY, Math.Min(item.Y0, item.Y1));
177.331 + maxValueY = Math.Max(maxValueY, Math.Max(item.Y0, item.Y1));
177.332 + }
177.333 +
177.334 + this.MinX = minValueX;
177.335 + this.MaxX = maxValueX;
177.336 + this.MinY = minValueY;
177.337 + this.MaxY = maxValueY;
177.338 + }
177.339 + }
177.340 +}
177.341 \ No newline at end of file
178.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
178.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/TornadoBarItem.cs Sat Jun 08 16:53:22 2013 +0000
178.3 @@ -0,0 +1,147 @@
178.4 +// --------------------------------------------------------------------------------------------------------------------
178.5 +// <copyright file="TornadoBarItem.cs" company="OxyPlot">
178.6 +// The MIT License (MIT)
178.7 +//
178.8 +// Copyright (c) 2012 Oystein Bjorke
178.9 +//
178.10 +// Permission is hereby granted, free of charge, to any person obtaining a
178.11 +// copy of this software and associated documentation files (the
178.12 +// "Software"), to deal in the Software without restriction, including
178.13 +// without limitation the rights to use, copy, modify, merge, publish,
178.14 +// distribute, sublicense, and/or sell copies of the Software, and to
178.15 +// permit persons to whom the Software is furnished to do so, subject to
178.16 +// the following conditions:
178.17 +//
178.18 +// The above copyright notice and this permission notice shall be included
178.19 +// in all copies or substantial portions of the Software.
178.20 +//
178.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
178.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
178.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
178.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
178.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
178.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
178.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
178.28 +// </copyright>
178.29 +// <summary>
178.30 +// Represents an item for the TornadoBarSeries.
178.31 +// </summary>
178.32 +// --------------------------------------------------------------------------------------------------------------------
178.33 +namespace OxyPlot.Series
178.34 +{
178.35 + /// <summary>
178.36 + /// Represents an item for the TornadoBarSeries.
178.37 + /// </summary>
178.38 + public class TornadoBarItem : CategorizedItem, ICodeGenerating
178.39 + {
178.40 + /// <summary>
178.41 + /// Initializes a new instance of the <see cref="TornadoBarItem"/> class.
178.42 + /// </summary>
178.43 + public TornadoBarItem()
178.44 + {
178.45 + this.Minimum = double.NaN;
178.46 + this.Maximum = double.NaN;
178.47 + this.BaseValue = double.NaN;
178.48 + this.MinimumColor = null;
178.49 + this.MaximumColor = null;
178.50 + }
178.51 +
178.52 + /// <summary>
178.53 + /// Initializes a new instance of the <see cref="TornadoBarItem"/> class.
178.54 + /// </summary>
178.55 + /// <param name="minimum">
178.56 + /// The minimum.
178.57 + /// </param>
178.58 + /// <param name="maximum">
178.59 + /// The maximum.
178.60 + /// </param>
178.61 + /// <param name="baseValue">
178.62 + /// The base value.
178.63 + /// </param>
178.64 + /// <param name="minimumColor">
178.65 + /// The minimum color.
178.66 + /// </param>
178.67 + /// <param name="maximumColor">
178.68 + /// The maximum color.
178.69 + /// </param>
178.70 + public TornadoBarItem(
178.71 + double minimum,
178.72 + double maximum,
178.73 + double baseValue = double.NaN,
178.74 + OxyColor minimumColor = null,
178.75 + OxyColor maximumColor = null)
178.76 + {
178.77 + this.Minimum = minimum;
178.78 + this.Maximum = maximum;
178.79 + this.BaseValue = baseValue;
178.80 + this.MinimumColor = minimumColor;
178.81 + this.MaximumColor = maximumColor;
178.82 + }
178.83 +
178.84 + /// <summary>
178.85 + /// Gets or sets the base value.
178.86 + /// </summary>
178.87 + public double BaseValue { get; set; }
178.88 +
178.89 + /// <summary>
178.90 + /// Gets or sets the maximum.
178.91 + /// </summary>
178.92 + public double Maximum { get; set; }
178.93 +
178.94 + /// <summary>
178.95 + /// Gets or sets the color for the maximum bar.
178.96 + /// </summary>
178.97 + public OxyColor MaximumColor { get; set; }
178.98 +
178.99 + /// <summary>
178.100 + /// Gets or sets the minimum value.
178.101 + /// </summary>
178.102 + public double Minimum { get; set; }
178.103 +
178.104 + /// <summary>
178.105 + /// Gets or sets the color for the minimum bar.
178.106 + /// </summary>
178.107 + public OxyColor MinimumColor { get; set; }
178.108 +
178.109 + /// <summary>
178.110 + /// Returns c# code that generates this instance.
178.111 + /// </summary>
178.112 + /// <returns>
178.113 + /// C# code.
178.114 + /// </returns>
178.115 + public string ToCode()
178.116 + {
178.117 + if (this.MaximumColor != null)
178.118 + {
178.119 + return CodeGenerator.FormatConstructor(
178.120 + this.GetType(),
178.121 + "{0},{1},{2},{3},{4}",
178.122 + this.Minimum,
178.123 + this.Maximum,
178.124 + this.BaseValue,
178.125 + this.MinimumColor.ToCode(),
178.126 + this.MaximumColor.ToCode());
178.127 + }
178.128 +
178.129 + if (this.MinimumColor != null)
178.130 + {
178.131 + return CodeGenerator.FormatConstructor(
178.132 + this.GetType(),
178.133 + "{0},{1},{2},{3}",
178.134 + this.Minimum,
178.135 + this.Maximum,
178.136 + this.BaseValue,
178.137 + this.MinimumColor.ToCode());
178.138 + }
178.139 +
178.140 + if (!double.IsNaN(this.BaseValue))
178.141 + {
178.142 + return CodeGenerator.FormatConstructor(
178.143 + this.GetType(), "{0},{1},{2}", this.Minimum, this.Maximum, this.BaseValue);
178.144 + }
178.145 +
178.146 + return CodeGenerator.FormatConstructor(this.GetType(), "{0},{1}", this.Minimum, this.Maximum);
178.147 + }
178.148 +
178.149 + }
178.150 +}
178.151 \ No newline at end of file
179.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
179.2 +++ b/External/OxyPlot/OxyPlot/Series/BarSeries/TornadoBarSeries.cs Sat Jun 08 16:53:22 2013 +0000
179.3 @@ -0,0 +1,590 @@
179.4 +// --------------------------------------------------------------------------------------------------------------------
179.5 +// <copyright file="TornadoBarSeries.cs" company="OxyPlot">
179.6 +// The MIT License (MIT)
179.7 +//
179.8 +// Copyright (c) 2012 Oystein Bjorke
179.9 +//
179.10 +// Permission is hereby granted, free of charge, to any person obtaining a
179.11 +// copy of this software and associated documentation files (the
179.12 +// "Software"), to deal in the Software without restriction, including
179.13 +// without limitation the rights to use, copy, modify, merge, publish,
179.14 +// distribute, sublicense, and/or sell copies of the Software, and to
179.15 +// permit persons to whom the Software is furnished to do so, subject to
179.16 +// the following conditions:
179.17 +//
179.18 +// The above copyright notice and this permission notice shall be included
179.19 +// in all copies or substantial portions of the Software.
179.20 +//
179.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
179.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
179.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
179.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
179.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
179.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
179.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
179.28 +// </copyright>
179.29 +// <summary>
179.30 +// Represents a series that can be used to create tornado plots.
179.31 +// </summary>
179.32 +// --------------------------------------------------------------------------------------------------------------------
179.33 +namespace OxyPlot.Series
179.34 +{
179.35 + using System;
179.36 + using System.Collections.Generic;
179.37 + using System.Linq;
179.38 +
179.39 + using OxyPlot.Axes;
179.40 +
179.41 + /// <summary>
179.42 + /// Represents a series that can be used to create tornado plots.
179.43 + /// </summary>
179.44 + /// <remarks>
179.45 + /// See http://en.wikipedia.org/wiki/Tornado_diagram.
179.46 + /// </remarks>
179.47 + public class TornadoBarSeries : CategorizedSeries
179.48 + {
179.49 + /// <summary>
179.50 + /// The default fill color.
179.51 + /// </summary>
179.52 + private OxyColor defaultMaximumFillColor;
179.53 +
179.54 + /// <summary>
179.55 + /// The default minimum fill color.
179.56 + /// </summary>
179.57 + private OxyColor defaultMinimumFillColor;
179.58 +
179.59 + /// <summary>
179.60 + /// Initializes a new instance of the <see cref="TornadoBarSeries"/> class.
179.61 + /// </summary>
179.62 + public TornadoBarSeries()
179.63 + {
179.64 + this.Items = new List<TornadoBarItem>();
179.65 +
179.66 + this.MaximumFillColor = OxyColor.FromRgb(216, 82, 85);
179.67 + this.MinimumFillColor = OxyColor.FromRgb(84, 138, 209);
179.68 +
179.69 + this.StrokeColor = OxyColors.Black;
179.70 + this.StrokeThickness = 1;
179.71 + this.BarWidth = 1;
179.72 +
179.73 + this.TrackerFormatString = "{0}";
179.74 + this.LabelMargin = 4;
179.75 +
179.76 + this.MinimumLabelFormatString = "{0}";
179.77 + this.MaximumLabelFormatString = "{0}";
179.78 + }
179.79 +
179.80 + /// <summary>
179.81 + /// Gets or sets the width of the bars (as a fraction of the available width). The default value is 0.5 (50%)
179.82 + /// </summary>
179.83 + /// <value>
179.84 + /// The width of the bars.
179.85 + /// </value>
179.86 + public double BarWidth { get; set; }
179.87 +
179.88 + /// <summary>
179.89 + /// Gets or sets the base value.
179.90 + /// </summary>
179.91 + /// <value>
179.92 + /// The base value.
179.93 + /// </value>
179.94 + public double BaseValue { get; set; }
179.95 +
179.96 + /// <summary>
179.97 + /// Gets the tornado bar items.
179.98 + /// </summary>
179.99 + /// <value>
179.100 + /// The items.
179.101 + /// </value>
179.102 + public IList<TornadoBarItem> Items { get; private set; }
179.103 +
179.104 + /// <summary>
179.105 + /// Gets or sets the label color.
179.106 + /// </summary>
179.107 + public OxyColor LabelColor { get; set; }
179.108 +
179.109 + /// <summary>
179.110 + /// Gets or sets the label field.
179.111 + /// </summary>
179.112 + public string LabelField { get; set; }
179.113 +
179.114 + /// <summary>
179.115 + /// Gets or sets the label margins.
179.116 + /// </summary>
179.117 + public double LabelMargin { get; set; }
179.118 +
179.119 + /// <summary>
179.120 + /// Gets or sets the maximum value field.
179.121 + /// </summary>
179.122 + public string MaximumField { get; set; }
179.123 +
179.124 + /// <summary>
179.125 + /// Gets or sets the color of the interior of the Maximum bars.
179.126 + /// </summary>
179.127 + /// <value>
179.128 + /// The color.
179.129 + /// </value>
179.130 + public OxyColor MaximumFillColor { get; set; }
179.131 +
179.132 + /// <summary>
179.133 + /// Gets the actual fill color.
179.134 + /// </summary>
179.135 + /// <value>The actual color.</value>
179.136 + public OxyColor ActualMaximumFillColor
179.137 + {
179.138 + get { return this.MaximumFillColor ?? this.defaultMaximumFillColor; }
179.139 + }
179.140 +
179.141 + /// <summary>
179.142 + /// Gets or sets the format string for the maximum labels.
179.143 + /// </summary>
179.144 + public string MaximumLabelFormatString { get; set; }
179.145 +
179.146 + /// <summary>
179.147 + /// Gets or sets the minimum value field.
179.148 + /// </summary>
179.149 + public string MinimumField { get; set; }
179.150 +
179.151 + /// <summary>
179.152 + /// Gets or sets the default color of the interior of the Minimum bars.
179.153 + /// </summary>
179.154 + /// <value>
179.155 + /// The color.
179.156 + /// </value>
179.157 + public OxyColor MinimumFillColor { get; set; }
179.158 +
179.159 + /// <summary>
179.160 + /// Gets the actual minimum fill color.
179.161 + /// </summary>
179.162 + /// <value>The actual color.</value>
179.163 + public OxyColor ActualMinimumFillColor
179.164 + {
179.165 + get { return this.MinimumFillColor ?? this.defaultMinimumFillColor; }
179.166 + }
179.167 +
179.168 + /// <summary>
179.169 + /// Gets or sets the format string for the minimum labels.
179.170 + /// </summary>
179.171 + public string MinimumLabelFormatString { get; set; }
179.172 +
179.173 + /// <summary>
179.174 + /// Gets or sets the color of the border around the bars.
179.175 + /// </summary>
179.176 + /// <value>
179.177 + /// The color of the stroke.
179.178 + /// </value>
179.179 + public OxyColor StrokeColor { get; set; }
179.180 +
179.181 + /// <summary>
179.182 + /// Gets or sets the thickness of the bar border strokes.
179.183 + /// </summary>
179.184 + /// <value>
179.185 + /// The stroke thickness.
179.186 + /// </value>
179.187 + public double StrokeThickness { get; set; }
179.188 +
179.189 + /// <summary>
179.190 + /// Gets or sets the actual rectangles for the maximum bars.
179.191 + /// </summary>
179.192 + protected internal IList<OxyRect> ActualMaximumBarRectangles { get; set; }
179.193 +
179.194 + /// <summary>
179.195 + /// Gets or sets the actual rectangles for the minimum bars.
179.196 + /// </summary>
179.197 + protected internal IList<OxyRect> ActualMinimumBarRectangles { get; set; }
179.198 +
179.199 + /// <summary>
179.200 + /// Gets or sets the valid items
179.201 + /// </summary>
179.202 + protected internal IList<TornadoBarItem> ValidItems { get; set; }
179.203 +
179.204 + /// <summary>
179.205 + /// Gets or sets the dictionary which stores the index-inversion for the valid items
179.206 + /// </summary>
179.207 + protected internal Dictionary<int, int> ValidItemsIndexInversion { get; set; }
179.208 +
179.209 + /// <summary>
179.210 + /// Gets the point in the dataset that is nearest the specified point.
179.211 + /// </summary>
179.212 + /// <param name="point">
179.213 + /// The point.
179.214 + /// </param>
179.215 + /// <param name="interpolate">
179.216 + /// The interpolate.
179.217 + /// </param>
179.218 + /// <returns>
179.219 + /// A TrackerHitResult for the current hit.
179.220 + /// </returns>
179.221 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
179.222 + {
179.223 + for (int i = 0; i < this.ActualMinimumBarRectangles.Count; i++)
179.224 + {
179.225 + var r = this.ActualMinimumBarRectangles[i];
179.226 + if (r.Contains(point))
179.227 + {
179.228 + var item = (TornadoBarItem)this.GetItem(this.ValidItemsIndexInversion[i]);
179.229 + var categoryIndex = item.GetCategoryIndex(i);
179.230 + var value = this.ValidItems[i].Minimum;
179.231 + var dp = new DataPoint(categoryIndex, value);
179.232 + var text = StringHelper.Format(this.ActualCulture, this.TrackerFormatString, item, value);
179.233 + return new TrackerHitResult(this, dp, point, item, i, text);
179.234 + }
179.235 +
179.236 + r = this.ActualMaximumBarRectangles[i];
179.237 + if (r.Contains(point))
179.238 + {
179.239 + var item = (TornadoBarItem)this.GetItem(this.ValidItemsIndexInversion[i]);
179.240 + var categoryIndex = item.GetCategoryIndex(i);
179.241 + var value = this.ValidItems[i].Maximum;
179.242 + var dp = new DataPoint(categoryIndex, value);
179.243 + var text = StringHelper.Format(this.ActualCulture, this.TrackerFormatString, item, value);
179.244 + return new TrackerHitResult(this, dp, point, item, i, text);
179.245 + }
179.246 + }
179.247 +
179.248 + return null;
179.249 + }
179.250 +
179.251 + /// <summary>
179.252 + /// Checks if the specified value is valid.
179.253 + /// </summary>
179.254 + /// <param name="v">
179.255 + /// The value.
179.256 + /// </param>
179.257 + /// <param name="yaxis">
179.258 + /// The y axis.
179.259 + /// </param>
179.260 + /// <returns>
179.261 + /// True if the value is valid.
179.262 + /// </returns>
179.263 + public virtual bool IsValidPoint(double v, Axis yaxis)
179.264 + {
179.265 + return !double.IsNaN(v) && !double.IsInfinity(v);
179.266 + }
179.267 +
179.268 + /// <summary>
179.269 + /// Renders the Series on the specified rendering context.
179.270 + /// </summary>
179.271 + /// <param name="rc">
179.272 + /// The rendering context.
179.273 + /// </param>
179.274 + /// <param name="model">
179.275 + /// The model.
179.276 + /// </param>
179.277 + public override void Render(IRenderContext rc, PlotModel model)
179.278 + {
179.279 + this.ActualMinimumBarRectangles = new List<OxyRect>();
179.280 + this.ActualMaximumBarRectangles = new List<OxyRect>();
179.281 +
179.282 + if (this.ValidItems.Count == 0)
179.283 + {
179.284 + return;
179.285 + }
179.286 +
179.287 + var clippingRect = this.GetClippingRect();
179.288 + var categoryAxis = this.GetCategoryAxis();
179.289 + var actualBarWidth = this.GetActualBarWidth();
179.290 +
179.291 + for (var i = 0; i < this.ValidItems.Count; i++)
179.292 + {
179.293 + var item = this.ValidItems[i];
179.294 +
179.295 + var categoryIndex = item.GetCategoryIndex(i);
179.296 +
179.297 + var baseValue = double.IsNaN(item.BaseValue) ? this.BaseValue : item.BaseValue;
179.298 +
179.299 + var p0 = this.Transform(item.Minimum, categoryIndex - 0.5 + categoryAxis.BarOffset[categoryIndex]);
179.300 + var p1 = this.Transform(
179.301 + item.Maximum, categoryIndex - 0.5 + categoryAxis.BarOffset[categoryIndex] + actualBarWidth);
179.302 + var p2 = this.Transform(baseValue, categoryIndex - 0.5 + categoryAxis.BarOffset[categoryIndex]);
179.303 + p2.X = (int)p2.X;
179.304 +
179.305 + var minimumRectangle = OxyRect.Create(p0.X, p0.Y, p2.X, p1.Y);
179.306 + var maximumRectangle = OxyRect.Create(p2.X, p0.Y, p1.X, p1.Y);
179.307 +
179.308 + this.ActualMinimumBarRectangles.Add(minimumRectangle);
179.309 + this.ActualMaximumBarRectangles.Add(maximumRectangle);
179.310 +
179.311 + rc.DrawClippedRectangleAsPolygon(
179.312 + minimumRectangle,
179.313 + clippingRect,
179.314 + item.MinimumColor ?? this.ActualMinimumFillColor,
179.315 + this.StrokeColor,
179.316 + this.StrokeThickness);
179.317 + rc.DrawClippedRectangleAsPolygon(
179.318 + maximumRectangle,
179.319 + clippingRect,
179.320 + item.MaximumColor ?? this.ActualMaximumFillColor,
179.321 + this.StrokeColor,
179.322 + this.StrokeThickness);
179.323 +
179.324 + if (this.MinimumLabelFormatString != null)
179.325 + {
179.326 + var s = StringHelper.Format(
179.327 + this.ActualCulture,
179.328 + this.MinimumLabelFormatString,
179.329 + this.GetItem(this.ValidItemsIndexInversion[i]),
179.330 + item.Minimum);
179.331 + var pt = new ScreenPoint(
179.332 + minimumRectangle.Left - this.LabelMargin, (minimumRectangle.Top + minimumRectangle.Bottom) / 2);
179.333 +
179.334 + rc.DrawClippedText(
179.335 + clippingRect,
179.336 + pt,
179.337 + s,
179.338 + this.ActualTextColor,
179.339 + this.ActualFont,
179.340 + this.ActualFontSize,
179.341 + this.ActualFontWeight,
179.342 + 0,
179.343 + HorizontalAlignment.Right,
179.344 + VerticalAlignment.Middle);
179.345 + }
179.346 +
179.347 + if (this.MaximumLabelFormatString != null)
179.348 + {
179.349 + var s = StringHelper.Format(
179.350 + this.ActualCulture,
179.351 + this.MaximumLabelFormatString,
179.352 + this.GetItem(this.ValidItemsIndexInversion[i]),
179.353 + item.Maximum);
179.354 + var pt = new ScreenPoint(
179.355 + maximumRectangle.Right + this.LabelMargin, (maximumRectangle.Top + maximumRectangle.Bottom) / 2);
179.356 +
179.357 + rc.DrawClippedText(
179.358 + clippingRect,
179.359 + pt,
179.360 + s,
179.361 + this.ActualTextColor,
179.362 + this.ActualFont,
179.363 + this.ActualFontSize,
179.364 + this.ActualFontWeight,
179.365 + 0,
179.366 + HorizontalAlignment.Left,
179.367 + VerticalAlignment.Middle);
179.368 + }
179.369 + }
179.370 + }
179.371 +
179.372 + /// <summary>
179.373 + /// Renders the legend symbol on the specified rendering context.
179.374 + /// </summary>
179.375 + /// <param name="rc">
179.376 + /// The rendering context.
179.377 + /// </param>
179.378 + /// <param name="legendBox">
179.379 + /// The legend rectangle.
179.380 + /// </param>
179.381 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
179.382 + {
179.383 + double xmid = (legendBox.Left + legendBox.Right) / 2;
179.384 + double ymid = (legendBox.Top + legendBox.Bottom) / 2;
179.385 + double height = (legendBox.Bottom - legendBox.Top) * 0.8;
179.386 + double width = height;
179.387 + rc.DrawRectangleAsPolygon(
179.388 + new OxyRect(xmid - (0.5 * width), ymid - (0.5 * height), 0.5 * width, height),
179.389 + this.ActualMinimumFillColor,
179.390 + this.StrokeColor,
179.391 + this.StrokeThickness);
179.392 + rc.DrawRectangleAsPolygon(
179.393 + new OxyRect(xmid, ymid - (0.5 * height), 0.5 * width, height),
179.394 + this.ActualMaximumFillColor,
179.395 + this.StrokeColor,
179.396 + this.StrokeThickness);
179.397 + }
179.398 +
179.399 + /// <summary>
179.400 + /// Gets or sets the width/height of the columns/bars (as a fraction of the available space).
179.401 + /// </summary>
179.402 + /// <returns>
179.403 + /// The fractional width.
179.404 + /// </returns>
179.405 + /// <value>
179.406 + /// The width of the bars.
179.407 + /// </value>
179.408 + /// <remarks>
179.409 + /// The available space will be determined by the GapWidth of the CategoryAxis used by this series.
179.410 + /// </remarks>
179.411 + internal override double GetBarWidth()
179.412 + {
179.413 + return this.BarWidth;
179.414 + }
179.415 +
179.416 + /// <summary>
179.417 + /// Gets the items of this series.
179.418 + /// </summary>
179.419 + /// <returns>
179.420 + /// The items.
179.421 + /// </returns>
179.422 + protected internal override IList<CategorizedItem> GetItems()
179.423 + {
179.424 + return this.Items.Cast<CategorizedItem>().ToList();
179.425 + }
179.426 +
179.427 + /// <summary>
179.428 + /// Check if the data series is using the specified axis.
179.429 + /// </summary>
179.430 + /// <param name="axis">
179.431 + /// An axis which should be checked if used
179.432 + /// </param>
179.433 + /// <returns>
179.434 + /// True if the axis is in use.
179.435 + /// </returns>
179.436 + protected internal override bool IsUsing(Axis axis)
179.437 + {
179.438 + return this.XAxis == axis || this.YAxis == axis;
179.439 + }
179.440 +
179.441 + /// <summary>
179.442 + /// The set default values.
179.443 + /// </summary>
179.444 + /// <param name="model">
179.445 + /// The model.
179.446 + /// </param>
179.447 + protected internal override void SetDefaultValues(PlotModel model)
179.448 + {
179.449 + if (this.MaximumFillColor == null)
179.450 + {
179.451 + this.defaultMaximumFillColor = model.GetDefaultColor();
179.452 + }
179.453 +
179.454 + if (this.MinimumFillColor == null)
179.455 + {
179.456 + this.defaultMinimumFillColor = model.GetDefaultColor();
179.457 + }
179.458 + }
179.459 +
179.460 + /// <summary>
179.461 + /// Updates the axis maximum and minimum values.
179.462 + /// </summary>
179.463 + protected internal override void UpdateAxisMaxMin()
179.464 + {
179.465 + this.XAxis.Include(this.MinX);
179.466 + this.XAxis.Include(this.MaxX);
179.467 + }
179.468 +
179.469 + /// <summary>
179.470 + /// Updates the data.
179.471 + /// </summary>
179.472 + protected internal override void UpdateData()
179.473 + {
179.474 + if (this.ItemsSource != null)
179.475 + {
179.476 + this.Items.Clear();
179.477 +
179.478 + var filler = new ListFiller<TornadoBarItem>();
179.479 + filler.Add(this.MinimumField, (item, value) => item.Minimum = Convert.ToDouble(value));
179.480 + filler.Add(this.MaximumField, (item, value) => item.Maximum = Convert.ToDouble(value));
179.481 + filler.FillT(this.Items, this.ItemsSource);
179.482 + }
179.483 + }
179.484 +
179.485 + /// <summary>
179.486 + /// Updates the maximum/minimum value on the value axis from the bar values.
179.487 + /// </summary>
179.488 + protected internal override void UpdateMaxMin()
179.489 + {
179.490 + base.UpdateMaxMin();
179.491 +
179.492 + if (this.ValidItems == null || this.ValidItems.Count == 0)
179.493 + {
179.494 + return;
179.495 + }
179.496 +
179.497 + double minValue = double.MaxValue;
179.498 + double maxValue = double.MinValue;
179.499 +
179.500 + foreach (var item in this.ValidItems)
179.501 + {
179.502 + minValue = Math.Min(minValue, item.Minimum);
179.503 + maxValue = Math.Max(maxValue, item.Maximum);
179.504 + }
179.505 +
179.506 + this.MinX = minValue;
179.507 + this.MaxX = maxValue;
179.508 + }
179.509 +
179.510 + /// <summary>
179.511 + /// Updates the valid items
179.512 + /// </summary>
179.513 + protected internal override void UpdateValidData()
179.514 + {
179.515 + this.ValidItems = new List<TornadoBarItem>();
179.516 + this.ValidItemsIndexInversion = new Dictionary<int, int>();
179.517 + var valueAxis = this.GetValueAxis();
179.518 +
179.519 + for (var i = 0; i < this.Items.Count; i++)
179.520 + {
179.521 + var item = this.Items[i];
179.522 + if (valueAxis.IsValidValue(item.Minimum) && valueAxis.IsValidValue(item.Maximum))
179.523 + {
179.524 + this.ValidItemsIndexInversion.Add(this.ValidItems.Count, i);
179.525 + this.ValidItems.Add(item);
179.526 + }
179.527 + }
179.528 + }
179.529 +
179.530 + /// <summary>
179.531 + /// Gets the actual width/height of the items of this series.
179.532 + /// </summary>
179.533 + /// <returns>
179.534 + /// The width or height.
179.535 + /// </returns>
179.536 + /// <remarks>
179.537 + /// The actual width is also influenced by the GapWidth of the CategoryAxis used by this series.
179.538 + /// </remarks>
179.539 + protected override double GetActualBarWidth()
179.540 + {
179.541 + var categoryAxis = this.GetCategoryAxis();
179.542 + return this.BarWidth / (1 + categoryAxis.GapWidth) / categoryAxis.MaxWidth;
179.543 + }
179.544 +
179.545 + /// <summary>
179.546 + /// Gets the category axis.
179.547 + /// </summary>
179.548 + /// <returns>
179.549 + /// The category axis.
179.550 + /// </returns>
179.551 + protected override CategoryAxis GetCategoryAxis()
179.552 + {
179.553 + var categoryAxis = this.YAxis as CategoryAxis;
179.554 + if (categoryAxis == null)
179.555 + {
179.556 + throw new InvalidOperationException("No category axis defined.");
179.557 + }
179.558 +
179.559 + return categoryAxis;
179.560 + }
179.561 +
179.562 + /// <summary>
179.563 + /// Gets the item at the specified index.
179.564 + /// </summary>
179.565 + /// <param name="i">
179.566 + /// The index of the item.
179.567 + /// </param>
179.568 + /// <returns>
179.569 + /// The item of the index.
179.570 + /// </returns>
179.571 + protected override object GetItem(int i)
179.572 + {
179.573 + if (this.ItemsSource != null || this.Items == null || this.Items.Count == 0)
179.574 + {
179.575 + return base.GetItem(i);
179.576 + }
179.577 +
179.578 + return this.Items[i];
179.579 + }
179.580 +
179.581 + /// <summary>
179.582 + /// Gets the value axis.
179.583 + /// </summary>
179.584 + /// <returns>
179.585 + /// The value axis.
179.586 + /// </returns>
179.587 + private Axis GetValueAxis()
179.588 + {
179.589 + return this.XAxis;
179.590 + }
179.591 +
179.592 + }
179.593 +}
179.594 \ No newline at end of file
180.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
180.2 +++ b/External/OxyPlot/OxyPlot/Series/BoxPlotItem.cs Sat Jun 08 16:53:22 2013 +0000
180.3 @@ -0,0 +1,167 @@
180.4 +// --------------------------------------------------------------------------------------------------------------------
180.5 +// <copyright file="BoxPlotItem.cs" company="OxyPlot">
180.6 +// The MIT License (MIT)
180.7 +//
180.8 +// Copyright (c) 2012 Oystein Bjorke
180.9 +//
180.10 +// Permission is hereby granted, free of charge, to any person obtaining a
180.11 +// copy of this software and associated documentation files (the
180.12 +// "Software"), to deal in the Software without restriction, including
180.13 +// without limitation the rights to use, copy, modify, merge, publish,
180.14 +// distribute, sublicense, and/or sell copies of the Software, and to
180.15 +// permit persons to whom the Software is furnished to do so, subject to
180.16 +// the following conditions:
180.17 +//
180.18 +// The above copyright notice and this permission notice shall be included
180.19 +// in all copies or substantial portions of the Software.
180.20 +//
180.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
180.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
180.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
180.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
180.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
180.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
180.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
180.28 +// </copyright>
180.29 +// <summary>
180.30 +// Represents an item in a BoxPlotSeries.
180.31 +// </summary>
180.32 +// --------------------------------------------------------------------------------------------------------------------
180.33 +namespace OxyPlot.Series
180.34 +{
180.35 + using System.Collections.Generic;
180.36 +
180.37 + /// <summary>
180.38 + /// Represents an item in a <see cref="BoxPlotSeries"/>.
180.39 + /// </summary>
180.40 + public struct BoxPlotItem
180.41 + {
180.42 + /// <summary>
180.43 + /// Initializes a new instance of the <see cref="BoxPlotItem"/> struct.
180.44 + /// </summary>
180.45 + /// <param name="x">
180.46 + /// The x.
180.47 + /// </param>
180.48 + /// <param name="lowerWhisker">
180.49 + /// The lower whisker.
180.50 + /// </param>
180.51 + /// <param name="boxBottom">
180.52 + /// The box bottom.
180.53 + /// </param>
180.54 + /// <param name="median">
180.55 + /// The median.
180.56 + /// </param>
180.57 + /// <param name="boxTop">
180.58 + /// The box top.
180.59 + /// </param>
180.60 + /// <param name="upperWhisker">
180.61 + /// The upper whisker.
180.62 + /// </param>
180.63 + /// <param name="outliers">
180.64 + /// The outliers.
180.65 + /// </param>
180.66 + /// <param name="tag">
180.67 + /// The tag.
180.68 + /// </param>
180.69 + public BoxPlotItem(
180.70 + double x,
180.71 + double lowerWhisker,
180.72 + double boxBottom,
180.73 + double median,
180.74 + double boxTop,
180.75 + double upperWhisker,
180.76 + IList<double> outliers,
180.77 + object tag = null)
180.78 + : this()
180.79 + {
180.80 + this.X = x;
180.81 + this.LowerWhisker = lowerWhisker;
180.82 + this.BoxBottom = boxBottom;
180.83 + this.Median = median;
180.84 + this.BoxTop = boxTop;
180.85 + this.UpperWhisker = upperWhisker;
180.86 + this.Outliers = outliers;
180.87 + this.Tag = tag;
180.88 + }
180.89 +
180.90 + /// <summary>
180.91 + /// Gets or sets the box bottom value (usually the 25th percentile, Q1).
180.92 + /// </summary>
180.93 + /// <value> The lower quartile value. </value>
180.94 + public double BoxBottom { get; set; }
180.95 +
180.96 + /// <summary>
180.97 + /// Gets or sets the box top value (usually the 75th percentile, Q3)).
180.98 + /// </summary>
180.99 + /// <value> The box top value. </value>
180.100 + public double BoxTop { get; set; }
180.101 +
180.102 + /// <summary>
180.103 + /// Gets or sets the lower whisker value.
180.104 + /// </summary>
180.105 + /// <value> The lower whisker value. </value>
180.106 + public double LowerWhisker { get; set; }
180.107 +
180.108 + /// <summary>
180.109 + /// Gets or sets the median.
180.110 + /// </summary>
180.111 + /// <value> The median. </value>
180.112 + public double Median { get; set; }
180.113 +
180.114 + /// <summary>
180.115 + /// Gets or sets the outliers.
180.116 + /// </summary>
180.117 + /// <value> The outliers. </value>
180.118 + public IList<double> Outliers { get; set; }
180.119 +
180.120 + /// <summary>
180.121 + /// Gets or sets the tag.
180.122 + /// </summary>
180.123 + /// <value> The tag. </value>
180.124 + public object Tag { get; set; }
180.125 +
180.126 + /// <summary>
180.127 + /// Gets or sets the upper whisker value.
180.128 + /// </summary>
180.129 + /// <value> The upper whisker value. </value>
180.130 + public double UpperWhisker { get; set; }
180.131 +
180.132 + /// <summary>
180.133 + /// Gets a list of all the values in the item.
180.134 + /// </summary>
180.135 + public IList<double> Values
180.136 + {
180.137 + get
180.138 + {
180.139 + var values = new List<double> { this.LowerWhisker, this.BoxBottom, this.Median, this.BoxTop, this.UpperWhisker };
180.140 + values.AddRange(this.Outliers);
180.141 + return values;
180.142 + }
180.143 + }
180.144 +
180.145 + /// <summary>
180.146 + /// Gets or sets the X value.
180.147 + /// </summary>
180.148 + /// <value> The X value. </value>
180.149 + public double X { get; set; }
180.150 +
180.151 + /// <summary>
180.152 + /// Returns a <see cref="System.String"/> that represents this instance.
180.153 + /// </summary>
180.154 + /// <returns>
180.155 + /// A <see cref="System.String"/> that represents this instance.
180.156 + /// </returns>
180.157 + public override string ToString()
180.158 + {
180.159 + return string.Format(
180.160 + "{0} {1} {2} {3} {4} {5} ",
180.161 + this.X,
180.162 + this.LowerWhisker,
180.163 + this.BoxBottom,
180.164 + this.Median,
180.165 + this.BoxTop,
180.166 + this.UpperWhisker);
180.167 + }
180.168 +
180.169 + }
180.170 +}
180.171 \ No newline at end of file
181.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
181.2 +++ b/External/OxyPlot/OxyPlot/Series/BoxPlotSeries.cs Sat Jun 08 16:53:22 2013 +0000
181.3 @@ -0,0 +1,615 @@
181.4 +// --------------------------------------------------------------------------------------------------------------------
181.5 +// <copyright file="BoxPlotSeries.cs" company="OxyPlot">
181.6 +// The MIT License (MIT)
181.7 +//
181.8 +// Copyright (c) 2012 Oystein Bjorke
181.9 +//
181.10 +// Permission is hereby granted, free of charge, to any person obtaining a
181.11 +// copy of this software and associated documentation files (the
181.12 +// "Software"), to deal in the Software without restriction, including
181.13 +// without limitation the rights to use, copy, modify, merge, publish,
181.14 +// distribute, sublicense, and/or sell copies of the Software, and to
181.15 +// permit persons to whom the Software is furnished to do so, subject to
181.16 +// the following conditions:
181.17 +//
181.18 +// The above copyright notice and this permission notice shall be included
181.19 +// in all copies or substantial portions of the Software.
181.20 +//
181.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
181.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
181.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
181.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
181.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
181.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
181.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
181.28 +// </copyright>
181.29 +// <summary>
181.30 +// Represents a series for box plots.
181.31 +// </summary>
181.32 +// --------------------------------------------------------------------------------------------------------------------
181.33 +
181.34 +namespace OxyPlot.Series
181.35 +{
181.36 + using System.Collections.Generic;
181.37 + using System.Linq;
181.38 +
181.39 + using OxyPlot.Axes;
181.40 +
181.41 + /// <summary>
181.42 + /// Represents a series for box plots.
181.43 + /// </summary>
181.44 + public class BoxPlotSeries : XYAxisSeries
181.45 + {
181.46 + /// <summary>
181.47 + /// Initializes a new instance of the <see cref="BoxPlotSeries"/> class.
181.48 + /// </summary>
181.49 + public BoxPlotSeries()
181.50 + {
181.51 + this.Items = new List<BoxPlotItem>();
181.52 + this.TrackerFormatString =
181.53 + "X: {1:0.00}\nUpper Whisker: {2:0.00}\nThird Quartil: {3:0.00}\nMedian: {4:0.00}\nFirst Quartil: {5:0.00}\nLower Whisker: {6:0.00}";
181.54 + this.OutlierTrackerFormatString = "X: {1:0.00}\nY: {2:0.00}";
181.55 + this.Title = null;
181.56 + this.Fill = null;
181.57 + this.Stroke = OxyColors.Black;
181.58 + this.BoxWidth = 0.3;
181.59 + this.StrokeThickness = 1;
181.60 + this.MedianThickness = 2;
181.61 + this.OutlierSize = 2;
181.62 + this.OutlierType = MarkerType.Circle;
181.63 + this.MedianPointSize = 2;
181.64 + this.WhiskerWidth = 0.5;
181.65 + this.LineStyle = LineStyle.Solid;
181.66 + this.ShowMedianAsDot = false;
181.67 + this.ShowBox = true;
181.68 + }
181.69 +
181.70 + /// <summary>
181.71 + /// Gets or sets the width of the boxes (specified in x-axis units).
181.72 + /// </summary>
181.73 + /// <value>
181.74 + /// The width of the boxes.
181.75 + /// </value>
181.76 + public double BoxWidth { get; set; }
181.77 +
181.78 + /// <summary>
181.79 + /// Gets or sets the fill color. If null, this color will be automatically set.
181.80 + /// </summary>
181.81 + /// <value>
181.82 + /// The fill color.
181.83 + /// </value>
181.84 + public OxyColor Fill { get; set; }
181.85 +
181.86 + /// <summary>
181.87 + /// Gets or sets the box plot items.
181.88 + /// </summary>
181.89 + /// <value>
181.90 + /// The items.
181.91 + /// </value>
181.92 + public IList<BoxPlotItem> Items { get; set; }
181.93 +
181.94 + /// <summary>
181.95 + /// Gets or sets the line style.
181.96 + /// </summary>
181.97 + /// <value>
181.98 + /// The line style.
181.99 + /// </value>
181.100 + public LineStyle LineStyle { get; set; }
181.101 +
181.102 + /// <summary>
181.103 + /// Gets or sets the size of the median point.
181.104 + /// </summary>
181.105 + /// <remarks>
181.106 + /// This property is only used when MedianStyle = Dot.
181.107 + /// </remarks>
181.108 + public double MedianPointSize { get; set; }
181.109 +
181.110 + /// <summary>
181.111 + /// Gets or sets the median thickness, relative to the StrokeThickness.
181.112 + /// </summary>
181.113 + /// <value>
181.114 + /// The median thickness.
181.115 + /// </value>
181.116 + public double MedianThickness { get; set; }
181.117 +
181.118 + /// <summary>
181.119 + /// Gets or sets the diameter of the outlier circles (specified in points).
181.120 + /// </summary>
181.121 + /// <value>
181.122 + /// The size of the outlier.
181.123 + /// </value>
181.124 + public double OutlierSize { get; set; }
181.125 +
181.126 + /// <summary>
181.127 + /// Gets or sets the tracker format string for the outliers.
181.128 + /// </summary>
181.129 + /// <value>
181.130 + /// The tracker format string for the outliers.
181.131 + /// </value>
181.132 + /// <remarks>
181.133 + /// Use {0} for series title, {1} for x- and {2} for y-value.
181.134 + /// </remarks>
181.135 + public string OutlierTrackerFormatString { get; set; }
181.136 +
181.137 + /// <summary>
181.138 + /// Gets or sets the type of the outliers.
181.139 + /// </summary>
181.140 + /// <value>
181.141 + /// The type of the outliers.
181.142 + /// </value>
181.143 + /// <remarks>
181.144 + /// MarkerType.Custom is currently not supported.
181.145 + /// </remarks>
181.146 + public MarkerType OutlierType { get; set; }
181.147 +
181.148 + /// <summary>
181.149 + /// Gets or sets a value indicating whether to show the boxes.
181.150 + /// </summary>
181.151 + public bool ShowBox { get; set; }
181.152 +
181.153 + /// <summary>
181.154 + /// Gets or sets a value indicating whether to show the median as a dot.
181.155 + /// </summary>
181.156 + public bool ShowMedianAsDot { get; set; }
181.157 +
181.158 + /// <summary>
181.159 + /// Gets or sets the stroke.
181.160 + /// </summary>
181.161 + /// <value>
181.162 + /// The stroke.
181.163 + /// </value>
181.164 + public OxyColor Stroke { get; set; }
181.165 +
181.166 + /// <summary>
181.167 + /// Gets or sets the stroke thickness.
181.168 + /// </summary>
181.169 + /// <value>
181.170 + /// The stroke thickness.
181.171 + /// </value>
181.172 + public double StrokeThickness { get; set; }
181.173 +
181.174 + /// <summary>
181.175 + /// Gets or sets the width of the whiskers (relative to the BoxWidth).
181.176 + /// </summary>
181.177 + /// <value>
181.178 + /// The width of the whiskers.
181.179 + /// </value>
181.180 + public double WhiskerWidth { get; set; }
181.181 +
181.182 + /// <summary>
181.183 + /// Gets the nearest point.
181.184 + /// </summary>
181.185 + /// <param name="point">
181.186 + /// The point.
181.187 + /// </param>
181.188 + /// <param name="interpolate">
181.189 + /// interpolate if set to <c>true</c> .
181.190 + /// </param>
181.191 + /// <returns>
181.192 + /// A TrackerHitResult for the current hit.
181.193 + /// </returns>
181.194 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
181.195 + {
181.196 + if (this.XAxis == null || this.YAxis == null)
181.197 + {
181.198 + return null;
181.199 + }
181.200 +
181.201 + double minimumDistance = double.MaxValue;
181.202 + var result = new TrackerHitResult(this, DataPoint.Undefined, ScreenPoint.Undefined);
181.203 + foreach (var item in this.Items)
181.204 + {
181.205 + foreach (var outlier in item.Outliers)
181.206 + {
181.207 + var sp = this.Transform(item.X, outlier);
181.208 + double d = (sp - point).LengthSquared;
181.209 + if (d < minimumDistance)
181.210 + {
181.211 + result.DataPoint = new DataPoint(item.X, outlier);
181.212 + result.Position = sp;
181.213 + result.Item = item;
181.214 + result.Text = StringHelper.Format(
181.215 + this.ActualCulture,
181.216 + this.OutlierTrackerFormatString,
181.217 + item,
181.218 + this.Title,
181.219 + this.XAxis.GetValue(result.DataPoint.X),
181.220 + outlier);
181.221 + minimumDistance = d;
181.222 + }
181.223 + }
181.224 +
181.225 + // check if we are inside the box rectangle
181.226 + var rect = this.GetBoxRect(item);
181.227 + if (rect.Contains(point))
181.228 + {
181.229 + result.DataPoint = new DataPoint(item.X, this.YAxis.InverseTransform(point.Y));
181.230 + result.Position = this.Transform(result.DataPoint);
181.231 + result.Item = item;
181.232 +
181.233 + result.Text = StringHelper.Format(
181.234 + this.ActualCulture,
181.235 + this.TrackerFormatString,
181.236 + item,
181.237 + this.Title,
181.238 + this.XAxis.GetValue(result.DataPoint.X),
181.239 + item.UpperWhisker,
181.240 + item.BoxTop,
181.241 + item.Median,
181.242 + item.BoxBottom,
181.243 + item.LowerWhisker);
181.244 +
181.245 + minimumDistance = 0;
181.246 + }
181.247 +
181.248 + var topWhisker = this.Transform(item.X, item.UpperWhisker);
181.249 + var bottomWhisker = this.Transform(item.X, item.LowerWhisker);
181.250 +
181.251 + // check if we are near the line
181.252 + var p = ScreenPointHelper.FindPointOnLine(point, topWhisker, bottomWhisker);
181.253 + double d2 = (p - point).LengthSquared;
181.254 + if (d2 < minimumDistance)
181.255 + {
181.256 + result.DataPoint = this.InverseTransform(p);
181.257 + result.Position = this.Transform(result.DataPoint);
181.258 + result.Item = item;
181.259 + result.Text = StringHelper.Format(
181.260 + this.ActualCulture,
181.261 + this.TrackerFormatString,
181.262 + item,
181.263 + this.Title,
181.264 + this.XAxis.GetValue(result.DataPoint.X),
181.265 + item.UpperWhisker,
181.266 + item.BoxTop,
181.267 + item.Median,
181.268 + item.BoxBottom,
181.269 + item.LowerWhisker);
181.270 + minimumDistance = d2;
181.271 + }
181.272 + }
181.273 +
181.274 + if (minimumDistance < double.MaxValue)
181.275 + {
181.276 + return result;
181.277 + }
181.278 +
181.279 + return null;
181.280 + }
181.281 +
181.282 + /// <summary>
181.283 + /// Determines whether the specified item contains a valid point.
181.284 + /// </summary>
181.285 + /// <param name="item">
181.286 + /// The item.
181.287 + /// </param>
181.288 + /// <param name="xaxis">
181.289 + /// The x axis.
181.290 + /// </param>
181.291 + /// <param name="yaxis">
181.292 + /// The y axis.
181.293 + /// </param>
181.294 + /// <returns>
181.295 + /// <c>true</c> if the point is valid; otherwise, <c>false</c> .
181.296 + /// </returns>
181.297 + public virtual bool IsValidPoint(BoxPlotItem item, Axis xaxis, Axis yaxis)
181.298 + {
181.299 + return !double.IsNaN(item.X) && !double.IsInfinity(item.X) && !item.Values.Any(double.IsNaN)
181.300 + && !item.Values.Any(double.IsInfinity) && (xaxis != null && xaxis.IsValidValue(item.X))
181.301 + && (yaxis != null && item.Values.All(yaxis.IsValidValue));
181.302 + }
181.303 +
181.304 + /// <summary>
181.305 + /// Renders the series on the specified render context.
181.306 + /// </summary>
181.307 + /// <param name="rc">
181.308 + /// The rendering context.
181.309 + /// </param>
181.310 + /// <param name="model">
181.311 + /// The model.
181.312 + /// </param>
181.313 + public override void Render(IRenderContext rc, PlotModel model)
181.314 + {
181.315 + if (this.Items.Count == 0)
181.316 + {
181.317 + return;
181.318 + }
181.319 +
181.320 + var clippingRect = this.GetClippingRect();
181.321 +
181.322 + var outlierScreenPoints = new List<ScreenPoint>();
181.323 + var halfBoxWidth = this.BoxWidth * 0.5;
181.324 + var halfWhiskerWidth = halfBoxWidth * this.WhiskerWidth;
181.325 + var strokeColor = this.GetSelectableColor(this.Stroke);
181.326 + var fillColor = this.GetSelectableFillColor(this.Fill);
181.327 +
181.328 + foreach (var item in this.Items)
181.329 + {
181.330 + // Add the outlier points
181.331 + outlierScreenPoints.AddRange(item.Outliers.Select(outlier => this.Transform(item.X, outlier)));
181.332 +
181.333 + var topWhiskerTop = this.Transform(item.X, item.UpperWhisker);
181.334 + var topWhiskerBottom = this.Transform(item.X, item.BoxTop);
181.335 + var bottomWhiskerTop = this.Transform(item.X, item.BoxBottom);
181.336 + var bottomWhiskerBottom = this.Transform(item.X, item.LowerWhisker);
181.337 + rc.DrawClippedLine(
181.338 + new[] { topWhiskerTop, topWhiskerBottom },
181.339 + clippingRect,
181.340 + 0,
181.341 + strokeColor,
181.342 + this.StrokeThickness,
181.343 + this.LineStyle,
181.344 + OxyPenLineJoin.Miter,
181.345 + true);
181.346 + rc.DrawClippedLine(
181.347 + new[] { bottomWhiskerTop, bottomWhiskerBottom },
181.348 + clippingRect,
181.349 + 0,
181.350 + strokeColor,
181.351 + this.StrokeThickness,
181.352 + this.LineStyle,
181.353 + OxyPenLineJoin.Miter,
181.354 + true);
181.355 +
181.356 + // Draw the whiskers
181.357 + if (this.WhiskerWidth > 0)
181.358 + {
181.359 + var topWhiskerLine1 = this.Transform(item.X - halfWhiskerWidth, item.UpperWhisker);
181.360 + var topWhiskerLine2 = this.Transform(item.X + halfWhiskerWidth, item.UpperWhisker);
181.361 + var bottomWhiskerLine1 = this.Transform(item.X - halfWhiskerWidth, item.LowerWhisker);
181.362 + var bottomWhiskerLine2 = this.Transform(item.X + halfWhiskerWidth, item.LowerWhisker);
181.363 +
181.364 + rc.DrawClippedLine(
181.365 + new[] { topWhiskerLine1, topWhiskerLine2 },
181.366 + clippingRect,
181.367 + 0,
181.368 + strokeColor,
181.369 + this.StrokeThickness,
181.370 + LineStyle.Solid,
181.371 + OxyPenLineJoin.Miter,
181.372 + true);
181.373 + rc.DrawClippedLine(
181.374 + new[] { bottomWhiskerLine1, bottomWhiskerLine2 },
181.375 + clippingRect,
181.376 + 0,
181.377 + strokeColor,
181.378 + this.StrokeThickness,
181.379 + LineStyle.Solid,
181.380 + OxyPenLineJoin.Miter,
181.381 + true);
181.382 + }
181.383 +
181.384 + if (this.ShowBox)
181.385 + {
181.386 + // Draw the box
181.387 + var rect = this.GetBoxRect(item);
181.388 + rc.DrawClippedRectangleAsPolygon(rect, clippingRect, fillColor, strokeColor, this.StrokeThickness);
181.389 + }
181.390 +
181.391 + if (!this.ShowMedianAsDot)
181.392 + {
181.393 + // Draw the median line
181.394 + var medianLeft = this.Transform(item.X - halfBoxWidth, item.Median);
181.395 + var medianRight = this.Transform(item.X + halfBoxWidth, item.Median);
181.396 + rc.DrawClippedLine(
181.397 + new[] { medianLeft, medianRight },
181.398 + clippingRect,
181.399 + 0,
181.400 + strokeColor,
181.401 + this.StrokeThickness * this.MedianThickness,
181.402 + LineStyle.Solid,
181.403 + OxyPenLineJoin.Miter,
181.404 + true);
181.405 + }
181.406 + else
181.407 + {
181.408 + var mc = this.Transform(item.X, item.Median);
181.409 + if (clippingRect.Contains(mc))
181.410 + {
181.411 + var ellipseRect = new OxyRect(
181.412 + mc.X - this.MedianPointSize,
181.413 + mc.Y - this.MedianPointSize,
181.414 + this.MedianPointSize * 2,
181.415 + this.MedianPointSize * 2);
181.416 + rc.DrawEllipse(ellipseRect, fillColor, null, 0);
181.417 + }
181.418 + }
181.419 + }
181.420 +
181.421 + // Draw the outlier(s)
181.422 + var markerSizes = outlierScreenPoints.Select(o => this.OutlierSize).ToList();
181.423 + rc.DrawMarkers(
181.424 + outlierScreenPoints,
181.425 + clippingRect,
181.426 + this.OutlierType,
181.427 + null,
181.428 + markerSizes,
181.429 + fillColor,
181.430 + strokeColor,
181.431 + this.StrokeThickness);
181.432 + }
181.433 +
181.434 + /// <summary>
181.435 + /// Renders the legend symbol on the specified rendering context.
181.436 + /// </summary>
181.437 + /// <param name="rc">
181.438 + /// The rendering context.
181.439 + /// </param>
181.440 + /// <param name="legendBox">
181.441 + /// The legend rectangle.
181.442 + /// </param>
181.443 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
181.444 + {
181.445 + double xmid = (legendBox.Left + legendBox.Right) / 2;
181.446 + double ybottom = legendBox.Top + ((legendBox.Bottom - legendBox.Top) * 0.7);
181.447 + double ytop = legendBox.Top + ((legendBox.Bottom - legendBox.Top) * 0.3);
181.448 + double ymid = (ybottom + ytop) * 0.5;
181.449 +
181.450 + var halfBoxWidth = legendBox.Width * 0.24;
181.451 + var halfWhiskerWidth = halfBoxWidth * this.WhiskerWidth;
181.452 + const double LegendStrokeThickness = 1;
181.453 + var strokeColor = this.GetSelectableColor(this.Stroke);
181.454 + var fillColor = this.GetSelectableFillColor(this.Fill);
181.455 +
181.456 + rc.DrawLine(
181.457 + new[] { new ScreenPoint(xmid, legendBox.Top), new ScreenPoint(xmid, ytop) },
181.458 + strokeColor,
181.459 + LegendStrokeThickness,
181.460 + LineStyle.Solid.GetDashArray(),
181.461 + OxyPenLineJoin.Miter,
181.462 + true);
181.463 +
181.464 + rc.DrawLine(
181.465 + new[] { new ScreenPoint(xmid, ybottom), new ScreenPoint(xmid, legendBox.Bottom) },
181.466 + strokeColor,
181.467 + LegendStrokeThickness,
181.468 + LineStyle.Solid.GetDashArray(),
181.469 + OxyPenLineJoin.Miter,
181.470 + true);
181.471 +
181.472 + if (this.WhiskerWidth > 0)
181.473 + {
181.474 + // top whisker
181.475 + rc.DrawLine(
181.476 + new[]
181.477 + {
181.478 + new ScreenPoint(xmid - halfWhiskerWidth - 1, legendBox.Bottom),
181.479 + new ScreenPoint(xmid + halfWhiskerWidth, legendBox.Bottom)
181.480 + },
181.481 + strokeColor,
181.482 + LegendStrokeThickness,
181.483 + LineStyle.Solid.GetDashArray(),
181.484 + OxyPenLineJoin.Miter,
181.485 + true);
181.486 +
181.487 + // bottom whisker
181.488 + rc.DrawLine(
181.489 + new[]
181.490 + {
181.491 + new ScreenPoint(xmid - halfWhiskerWidth - 1, legendBox.Top),
181.492 + new ScreenPoint(xmid + halfWhiskerWidth, legendBox.Top)
181.493 + },
181.494 + strokeColor,
181.495 + LegendStrokeThickness,
181.496 + LineStyle.Solid.GetDashArray(),
181.497 + OxyPenLineJoin.Miter,
181.498 + true);
181.499 + }
181.500 +
181.501 + if (this.ShowBox)
181.502 + {
181.503 + // box
181.504 + rc.DrawRectangleAsPolygon(
181.505 + new OxyRect(xmid - halfBoxWidth, ytop, 2 * halfBoxWidth, ybottom - ytop),
181.506 + fillColor,
181.507 + strokeColor,
181.508 + LegendStrokeThickness);
181.509 + }
181.510 +
181.511 + // median
181.512 + if (!this.ShowMedianAsDot)
181.513 + {
181.514 + rc.DrawLine(
181.515 + new[] { new ScreenPoint(xmid - halfBoxWidth, ymid), new ScreenPoint(xmid + halfBoxWidth, ymid) },
181.516 + strokeColor,
181.517 + LegendStrokeThickness * this.MedianThickness,
181.518 + LineStyle.Solid.GetDashArray(),
181.519 + OxyPenLineJoin.Miter,
181.520 + true);
181.521 + }
181.522 + else
181.523 + {
181.524 + var ellipseRect = new OxyRect(
181.525 + xmid - this.MedianPointSize,
181.526 + ymid - this.MedianPointSize,
181.527 + this.MedianPointSize * 2,
181.528 + this.MedianPointSize * 2);
181.529 + rc.DrawEllipse(ellipseRect, fillColor, null);
181.530 + }
181.531 + }
181.532 +
181.533 + /// <summary>
181.534 + /// Updates the max/minimum values.
181.535 + /// </summary>
181.536 + protected internal override void UpdateMaxMin()
181.537 + {
181.538 + base.UpdateMaxMin();
181.539 + this.InternalUpdateMaxMin(this.Items);
181.540 + }
181.541 +
181.542 + /// <summary>
181.543 + /// Updates the max and min of the series.
181.544 + /// </summary>
181.545 + /// <param name="items">
181.546 + /// The items.
181.547 + /// </param>
181.548 + protected void InternalUpdateMaxMin(IList<BoxPlotItem> items)
181.549 + {
181.550 + if (items == null || items.Count == 0)
181.551 + {
181.552 + return;
181.553 + }
181.554 +
181.555 + double minx = this.MinX;
181.556 + double miny = this.MinY;
181.557 + double maxx = this.MaxX;
181.558 + double maxy = this.MaxY;
181.559 +
181.560 + foreach (var pt in items)
181.561 + {
181.562 + if (!this.IsValidPoint(pt, this.XAxis, this.YAxis))
181.563 + {
181.564 + continue;
181.565 + }
181.566 +
181.567 + var x = pt.X;
181.568 + if (x < minx || double.IsNaN(minx))
181.569 + {
181.570 + minx = x;
181.571 + }
181.572 +
181.573 + if (x > maxx || double.IsNaN(maxx))
181.574 + {
181.575 + maxx = x;
181.576 + }
181.577 +
181.578 + foreach (var y in pt.Values)
181.579 + {
181.580 + if (y < miny || double.IsNaN(miny))
181.581 + {
181.582 + miny = y;
181.583 + }
181.584 +
181.585 + if (y > maxy || double.IsNaN(maxy))
181.586 + {
181.587 + maxy = y;
181.588 + }
181.589 + }
181.590 + }
181.591 +
181.592 + this.MinX = minx;
181.593 + this.MinY = miny;
181.594 + this.MaxX = maxx;
181.595 + this.MaxY = maxy;
181.596 + }
181.597 +
181.598 + /// <summary>
181.599 + /// Gets the screen rectangle for the box.
181.600 + /// </summary>
181.601 + /// <param name="item">
181.602 + /// The box item.
181.603 + /// </param>
181.604 + /// <returns>
181.605 + /// A rectangle.
181.606 + /// </returns>
181.607 + private OxyRect GetBoxRect(BoxPlotItem item)
181.608 + {
181.609 + var halfBoxWidth = this.BoxWidth * 0.5;
181.610 +
181.611 + var boxTop = this.Transform(item.X - halfBoxWidth, item.BoxTop);
181.612 + var boxBottom = this.Transform(item.X + halfBoxWidth, item.BoxBottom);
181.613 +
181.614 + var rect = new OxyRect(boxTop.X, boxTop.Y, boxBottom.X - boxTop.X, boxBottom.Y - boxTop.Y);
181.615 + return rect;
181.616 + }
181.617 + }
181.618 +}
181.619 \ No newline at end of file
182.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
182.2 +++ b/External/OxyPlot/OxyPlot/Series/CandleStickSeries.cs Sat Jun 08 16:53:22 2013 +0000
182.3 @@ -0,0 +1,201 @@
182.4 +// --------------------------------------------------------------------------------------------------------------------
182.5 +// <copyright file="CandleStickSeries.cs" company="OxyPlot">
182.6 +// The MIT License (MIT)
182.7 +//
182.8 +// Copyright (c) 2012 Oystein Bjorke
182.9 +//
182.10 +// Permission is hereby granted, free of charge, to any person obtaining a
182.11 +// copy of this software and associated documentation files (the
182.12 +// "Software"), to deal in the Software without restriction, including
182.13 +// without limitation the rights to use, copy, modify, merge, publish,
182.14 +// distribute, sublicense, and/or sell copies of the Software, and to
182.15 +// permit persons to whom the Software is furnished to do so, subject to
182.16 +// the following conditions:
182.17 +//
182.18 +// The above copyright notice and this permission notice shall be included
182.19 +// in all copies or substantial portions of the Software.
182.20 +//
182.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
182.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
182.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
182.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
182.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
182.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
182.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
182.28 +// </copyright>
182.29 +// <summary>
182.30 +// Represents a series for candlestick charts.
182.31 +// </summary>
182.32 +// --------------------------------------------------------------------------------------------------------------------
182.33 +namespace OxyPlot.Series
182.34 +{
182.35 + using System;
182.36 +
182.37 + /// <summary>
182.38 + /// Represents a series for candlestick charts.
182.39 + /// </summary>
182.40 + /// <remarks>
182.41 + /// http://en.wikipedia.org/wiki/Candlestick_chart
182.42 + /// http://www.mathworks.com/help/toolbox/finance/candle.html
182.43 + /// </remarks>
182.44 + public class CandleStickSeries : HighLowSeries
182.45 + {
182.46 + /// <summary>
182.47 + /// Initializes a new instance of the <see cref = "CandleStickSeries" /> class.
182.48 + /// </summary>
182.49 + public CandleStickSeries()
182.50 + {
182.51 + this.CandleWidth = 10;
182.52 + }
182.53 +
182.54 + /// <summary>
182.55 + /// Initializes a new instance of the <see cref="CandleStickSeries"/> class.
182.56 + /// </summary>
182.57 + /// <param name="title">
182.58 + /// The title.
182.59 + /// </param>
182.60 + public CandleStickSeries(string title)
182.61 + : this()
182.62 + {
182.63 + this.Title = title;
182.64 + }
182.65 +
182.66 + /// <summary>
182.67 + /// Initializes a new instance of the <see cref="CandleStickSeries"/> class.
182.68 + /// </summary>
182.69 + /// <param name="color">
182.70 + /// The color.
182.71 + /// </param>
182.72 + /// <param name="strokeThickness">
182.73 + /// The stroke thickness.
182.74 + /// </param>
182.75 + /// <param name="title">
182.76 + /// The title.
182.77 + /// </param>
182.78 + public CandleStickSeries(OxyColor color, double strokeThickness = 1, string title = null)
182.79 + : this()
182.80 + {
182.81 + this.Color = color;
182.82 + this.StrokeThickness = strokeThickness;
182.83 + this.Title = title;
182.84 + }
182.85 +
182.86 + /// <summary>
182.87 + /// Gets or sets the width of the candle.
182.88 + /// </summary>
182.89 + /// <value>The width of the candle.</value>
182.90 + public double CandleWidth { get; set; }
182.91 +
182.92 + /// <summary>
182.93 + /// Renders the series on the specified rendering context.
182.94 + /// </summary>
182.95 + /// <param name="rc">
182.96 + /// The rendering context.
182.97 + /// </param>
182.98 + /// <param name="model">
182.99 + /// The owner plot model.
182.100 + /// </param>
182.101 + public override void Render(IRenderContext rc, PlotModel model)
182.102 + {
182.103 + if (this.Items.Count == 0)
182.104 + {
182.105 + return;
182.106 + }
182.107 +
182.108 + this.VerifyAxes();
182.109 +
182.110 + var clippingRect = this.GetClippingRect();
182.111 +
182.112 + foreach (var v in this.Items)
182.113 + {
182.114 + if (!this.IsValidItem(v, this.XAxis, this.YAxis))
182.115 + {
182.116 + continue;
182.117 + }
182.118 +
182.119 + if (this.StrokeThickness > 0 && this.LineStyle != LineStyle.None)
182.120 + {
182.121 + var high = this.Transform(v.X, v.High);
182.122 + var low = this.Transform(v.X, v.Low);
182.123 +
182.124 + if (double.IsNaN(v.Open) || double.IsNaN(v.Close))
182.125 + {
182.126 + rc.DrawClippedLine(
182.127 + new[] { low, high },
182.128 + clippingRect,
182.129 + 0,
182.130 + this.GetSelectableColor(this.ActualColor),
182.131 + this.StrokeThickness,
182.132 + this.LineStyle,
182.133 + this.LineJoin,
182.134 + false);
182.135 + }
182.136 + else
182.137 + {
182.138 + var open = this.Transform(v.X, v.Open);
182.139 + var close = this.Transform(v.X, v.Close);
182.140 + var max = new ScreenPoint(open.X, Math.Max(open.Y, close.Y));
182.141 + var min = new ScreenPoint(open.X, Math.Min(open.Y, close.Y));
182.142 +
182.143 + rc.DrawClippedLine(
182.144 + new[] { high, min },
182.145 + clippingRect,
182.146 + 0,
182.147 + this.GetSelectableColor(this.ActualColor),
182.148 + this.StrokeThickness,
182.149 + this.LineStyle,
182.150 + this.LineJoin,
182.151 + true);
182.152 +
182.153 + rc.DrawClippedLine(
182.154 + new[] { max, low },
182.155 + clippingRect,
182.156 + 0,
182.157 + this.GetSelectableColor(this.ActualColor),
182.158 + this.StrokeThickness,
182.159 + this.LineStyle,
182.160 + this.LineJoin,
182.161 + true);
182.162 + var openLeft = open;
182.163 + openLeft.X -= this.CandleWidth * 0.5;
182.164 + var closeRight = close;
182.165 + closeRight.X += this.CandleWidth * 0.5;
182.166 + var rect = new OxyRect(openLeft.X, min.Y, this.CandleWidth, max.Y - min.Y);
182.167 + rc.DrawClippedRectangleAsPolygon(
182.168 + rect, clippingRect, v.Open > v.Close ? this.GetSelectableFillColor(this.ActualColor) : null, this.GetSelectableColor(this.ActualColor), this.StrokeThickness);
182.169 + }
182.170 + }
182.171 + }
182.172 + }
182.173 +
182.174 + /// <summary>
182.175 + /// Renders the legend symbol for the series on the specified rendering context.
182.176 + /// </summary>
182.177 + /// <param name="rc">
182.178 + /// The rendering context.
182.179 + /// </param>
182.180 + /// <param name="legendBox">
182.181 + /// The bounding rectangle of the legend box.
182.182 + /// </param>
182.183 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
182.184 + {
182.185 + double xmid = (legendBox.Left + legendBox.Right) / 2;
182.186 + double yopen = legendBox.Top + ((legendBox.Bottom - legendBox.Top) * 0.7);
182.187 + double yclose = legendBox.Top + ((legendBox.Bottom - legendBox.Top) * 0.3);
182.188 + double[] dashArray = LineStyleHelper.GetDashArray(this.LineStyle);
182.189 + rc.DrawLine(
182.190 + new[] { new ScreenPoint(xmid, legendBox.Top), new ScreenPoint(xmid, legendBox.Bottom) },
182.191 + this.GetSelectableColor(this.ActualColor),
182.192 + this.StrokeThickness,
182.193 + dashArray,
182.194 + OxyPenLineJoin.Miter,
182.195 + true);
182.196 + rc.DrawRectangleAsPolygon(
182.197 + new OxyRect(xmid - (this.CandleWidth * 0.5), yclose, this.CandleWidth, yopen - yclose),
182.198 + this.GetSelectableFillColor(this.ActualColor),
182.199 + this.GetSelectableColor(this.ActualColor),
182.200 + this.StrokeThickness);
182.201 + }
182.202 +
182.203 + }
182.204 +}
182.205 \ No newline at end of file
183.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
183.2 +++ b/External/OxyPlot/OxyPlot/Series/ContourSeries.cs Sat Jun 08 16:53:22 2013 +0000
183.3 @@ -0,0 +1,770 @@
183.4 +// --------------------------------------------------------------------------------------------------------------------
183.5 +// <copyright file="ContourSeries.cs" company="OxyPlot">
183.6 +// The MIT License (MIT)
183.7 +//
183.8 +// Copyright (c) 2012 Oystein Bjorke
183.9 +//
183.10 +// Permission is hereby granted, free of charge, to any person obtaining a
183.11 +// copy of this software and associated documentation files (the
183.12 +// "Software"), to deal in the Software without restriction, including
183.13 +// without limitation the rights to use, copy, modify, merge, publish,
183.14 +// distribute, sublicense, and/or sell copies of the Software, and to
183.15 +// permit persons to whom the Software is furnished to do so, subject to
183.16 +// the following conditions:
183.17 +//
183.18 +// The above copyright notice and this permission notice shall be included
183.19 +// in all copies or substantial portions of the Software.
183.20 +//
183.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
183.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
183.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
183.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
183.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
183.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
183.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
183.28 +// </copyright>
183.29 +// <summary>
183.30 +// Represents a series for contour plots.
183.31 +// </summary>
183.32 +// --------------------------------------------------------------------------------------------------------------------
183.33 +namespace OxyPlot.Series
183.34 +{
183.35 + using System;
183.36 + using System.Collections.Generic;
183.37 + using System.Linq;
183.38 +
183.39 + /// <summary>
183.40 + /// Represents a series that renders contours.
183.41 + /// </summary>
183.42 + /// <remarks>
183.43 + /// See http://en.wikipedia.org/wiki/Contour_line and http://www.mathworks.se/help/techdoc/ref/contour.html.
183.44 + /// </remarks>
183.45 + public class ContourSeries : XYAxisSeries
183.46 + {
183.47 + /// <summary>
183.48 + /// The contour collection.
183.49 + /// </summary>
183.50 + private List<Contour> contours;
183.51 +
183.52 + /// <summary>
183.53 + /// The temporary segment collection.
183.54 + /// </summary>
183.55 + private List<ContourSegment> segments;
183.56 +
183.57 + /// <summary>
183.58 + /// The default color.
183.59 + /// </summary>
183.60 + private OxyColor defaultColor;
183.61 +
183.62 + /// <summary>
183.63 + /// Initializes a new instance of the <see cref = "ContourSeries" /> class.
183.64 + /// </summary>
183.65 + public ContourSeries()
183.66 + {
183.67 + this.ContourLevelStep = double.NaN;
183.68 +
183.69 + this.LabelSpacing = double.NaN;
183.70 + this.LabelStep = 1;
183.71 + this.LabelBackground = OxyColor.FromAColor(220, OxyColors.White);
183.72 +
183.73 + this.Color = null;
183.74 + this.StrokeThickness = 1.0;
183.75 + this.LineStyle = LineStyle.Solid;
183.76 +
183.77 + this.TrackerFormatString = "{1}: {2:0.####}\n{3}: {4:0.####}\n{5}: {6:0.####}";
183.78 + }
183.79 +
183.80 + /// <summary>
183.81 + /// Gets or sets the color.
183.82 + /// </summary>
183.83 + /// <value>The color.</value>
183.84 + public OxyColor Color { get; set; }
183.85 +
183.86 + /// <summary>
183.87 + /// Gets the actual color.
183.88 + /// </summary>
183.89 + /// <value>The actual color.</value>
183.90 + public OxyColor ActualColor
183.91 + {
183.92 + get { return this.Color ?? this.defaultColor; }
183.93 + }
183.94 +
183.95 + /// <summary>
183.96 + /// Gets or sets the column coordinates.
183.97 + /// </summary>
183.98 + /// <value>The column coordinates.</value>
183.99 + public double[] ColumnCoordinates { get; set; }
183.100 +
183.101 + /// <summary>
183.102 + /// Gets or sets the contour level step size.
183.103 + /// This property is not used if the ContourLevels vector is set.
183.104 + /// </summary>
183.105 + /// <value>The contour level step size.</value>
183.106 + public double ContourLevelStep { get; set; }
183.107 +
183.108 + /// <summary>
183.109 + /// Gets or sets the contour levels.
183.110 + /// </summary>
183.111 + /// <value>The contour levels.</value>
183.112 + public double[] ContourLevels { get; set; }
183.113 +
183.114 + /// <summary>
183.115 + /// Gets or sets the contour colors.
183.116 + /// </summary>
183.117 + /// <value>The contour colors.</value>
183.118 + /// <remarks>
183.119 + /// These colors will override the Color of the series.
183.120 + /// If there are less colors than the number of contour levels, the colors will cycle.
183.121 + /// </remarks>
183.122 + public OxyColor[] ContourColors { get; set; }
183.123 +
183.124 + /// <summary>
183.125 + /// Gets or sets the data.
183.126 + /// </summary>
183.127 + /// <value>The data.</value>
183.128 + public double[,] Data { get; set; }
183.129 +
183.130 + /// <summary>
183.131 + /// Gets or sets the text background color.
183.132 + /// </summary>
183.133 + /// <value>The text background color.</value>
183.134 + public OxyColor LabelBackground { get; set; }
183.135 +
183.136 + /// <summary>
183.137 + /// Gets or sets the format string for contour values.
183.138 + /// </summary>
183.139 + /// <value>The format string.</value>
183.140 + public string LabelFormatString { get; set; }
183.141 +
183.142 + /// <summary>
183.143 + /// Gets or sets the label spacing.
183.144 + /// </summary>
183.145 + /// <value>The label spacing.</value>
183.146 + public double LabelSpacing { get; set; }
183.147 +
183.148 + /// <summary>
183.149 + /// Gets or sets the label step (number of contours per label).
183.150 + /// </summary>
183.151 + /// <value>The label step.</value>
183.152 + public int LabelStep { get; set; }
183.153 +
183.154 + /// <summary>
183.155 + /// Gets or sets the line style.
183.156 + /// </summary>
183.157 + /// <value>The line style.</value>
183.158 + public LineStyle LineStyle { get; set; }
183.159 +
183.160 + /// <summary>
183.161 + /// Gets or sets the row coordinates.
183.162 + /// </summary>
183.163 + /// <value>The row coordinates.</value>
183.164 + public double[] RowCoordinates { get; set; }
183.165 +
183.166 + /// <summary>
183.167 + /// Gets or sets the stroke thickness.
183.168 + /// </summary>
183.169 + /// <value>The stroke thickness.</value>
183.170 + public double StrokeThickness { get; set; }
183.171 +
183.172 + /// <summary>
183.173 + /// Calculates the contours.
183.174 + /// </summary>
183.175 + public void CalculateContours()
183.176 + {
183.177 + if (this.Data == null)
183.178 + {
183.179 + return;
183.180 + }
183.181 +
183.182 + double[] actualContourLevels = this.ContourLevels;
183.183 +
183.184 + this.segments = new List<ContourSegment>();
183.185 + Conrec.RendererDelegate renderer = (startX, startY, endX, endY, contourLevel) =>
183.186 + this.segments.Add(new ContourSegment(new DataPoint(startX, startY), new DataPoint(endX, endY), contourLevel));
183.187 +
183.188 + if (actualContourLevels == null)
183.189 + {
183.190 + double max = this.Data[0, 0];
183.191 + double min = this.Data[0, 0];
183.192 + for (int i = 0; i < this.Data.GetUpperBound(0); i++)
183.193 + {
183.194 + for (int j = 0; j < this.Data.GetUpperBound(1); j++)
183.195 + {
183.196 + max = Math.Max(max, this.Data[i, j]);
183.197 + min = Math.Min(min, this.Data[i, j]);
183.198 + }
183.199 + }
183.200 +
183.201 + double actualStep = this.ContourLevelStep;
183.202 + if (double.IsNaN(actualStep))
183.203 + {
183.204 + double range = max - min;
183.205 + double step = range / 20;
183.206 + actualStep = Math.Pow(10, Math.Floor(step.GetExponent()));
183.207 + }
183.208 +
183.209 + max = max.ToUpperMultiple(actualStep);
183.210 + min = min.ToLowerMultiple(actualStep);
183.211 + actualContourLevels = ArrayHelper.CreateVector(min, max, actualStep);
183.212 + }
183.213 +
183.214 + Conrec.Contour(this.Data, this.RowCoordinates, this.ColumnCoordinates, actualContourLevels, renderer);
183.215 +
183.216 + this.JoinContourSegments();
183.217 +
183.218 + if (this.ContourColors != null && this.ContourColors.Length > 0)
183.219 + {
183.220 + foreach (var c in this.contours)
183.221 + {
183.222 + // get the index of the contour's level
183.223 + var index = IndexOf(actualContourLevels, c.ContourLevel);
183.224 + if (index >= 0)
183.225 + {
183.226 + // clamp the index to the range of the ContourColors array
183.227 + index = index % this.ContourColors.Length;
183.228 + c.Color = this.ContourColors[index];
183.229 + }
183.230 + }
183.231 + }
183.232 + }
183.233 +
183.234 + /// <summary>
183.235 + /// Gets the point in the dataset that is nearest the specified point.
183.236 + /// </summary>
183.237 + /// <param name="point">
183.238 + /// The point.
183.239 + /// </param>
183.240 + /// <param name="interpolate">
183.241 + /// The interpolate.
183.242 + /// </param>
183.243 + /// <returns>
183.244 + /// A hit result object.
183.245 + /// </returns>
183.246 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
183.247 + {
183.248 + TrackerHitResult result = null;
183.249 +
183.250 + var xaxisTitle = this.XAxis.Title ?? "X";
183.251 + var yaxisTitle = this.YAxis.Title ?? "Y";
183.252 + var zaxisTitle = "Z";
183.253 +
183.254 + foreach (var c in this.contours)
183.255 + {
183.256 + var r = interpolate ? this.GetNearestInterpolatedPointInternal(c.Points, point) : this.GetNearestPointInternal(c.Points, point);
183.257 + if (r != null)
183.258 + {
183.259 + if (result == null || result.Position.DistanceToSquared(point) > r.Position.DistanceToSquared(point))
183.260 + {
183.261 + result = r;
183.262 + result.Text = StringHelper.Format(
183.263 + this.ActualCulture,
183.264 + this.TrackerFormatString,
183.265 + null,
183.266 + this.Title,
183.267 + xaxisTitle,
183.268 + r.DataPoint.X,
183.269 + yaxisTitle,
183.270 + r.DataPoint.Y,
183.271 + zaxisTitle,
183.272 + c.ContourLevel);
183.273 + }
183.274 + }
183.275 + }
183.276 +
183.277 + return result;
183.278 + }
183.279 +
183.280 + /// <summary>
183.281 + /// Renders the series on the specified rendering context.
183.282 + /// </summary>
183.283 + /// <param name="rc">
183.284 + /// The rendering context.
183.285 + /// </param>
183.286 + /// <param name="model">
183.287 + /// The model.
183.288 + /// </param>
183.289 + public override void Render(IRenderContext rc, PlotModel model)
183.290 + {
183.291 + if (this.contours == null)
183.292 + {
183.293 + this.CalculateContours();
183.294 + }
183.295 +
183.296 + if (this.contours.Count == 0)
183.297 + {
183.298 + return;
183.299 + }
183.300 +
183.301 + this.VerifyAxes();
183.302 +
183.303 + var clippingRect = this.GetClippingRect();
183.304 +
183.305 + var contourLabels = new List<ContourLabel>();
183.306 +
183.307 + foreach (var contour in this.contours)
183.308 + {
183.309 + if (this.StrokeThickness > 0 && this.LineStyle != LineStyle.None)
183.310 + {
183.311 + var pts = new ScreenPoint[contour.Points.Count];
183.312 + {
183.313 + int i = 0;
183.314 + foreach (var pt in contour.Points)
183.315 + {
183.316 + pts[i++] = this.Transform(pt.X, pt.Y);
183.317 + }
183.318 + }
183.319 +
183.320 + rc.DrawClippedLine(
183.321 + pts,
183.322 + clippingRect,
183.323 + 4,
183.324 + this.GetSelectableColor(contour.Color ?? this.ActualColor),
183.325 + this.StrokeThickness,
183.326 + this.LineStyle,
183.327 + OxyPenLineJoin.Miter,
183.328 + false);
183.329 +
183.330 + // rc.DrawClippedPolygon(pts, clippingRect, 4, model.GetDefaultColor(), OxyColors.Black);
183.331 + if (pts.Length > 10)
183.332 + {
183.333 + this.AddContourLabels(contour, pts, clippingRect, contourLabels);
183.334 + }
183.335 + }
183.336 + }
183.337 +
183.338 + foreach (var cl in contourLabels)
183.339 + {
183.340 + this.RenderLabelBackground(rc, cl);
183.341 + }
183.342 +
183.343 + foreach (var cl in contourLabels)
183.344 + {
183.345 + this.RenderLabel(rc, cl);
183.346 + }
183.347 + }
183.348 +
183.349 + /// <summary>
183.350 + /// Sets default values from the plotmodel.
183.351 + /// </summary>
183.352 + /// <param name="model">
183.353 + /// The plot model.
183.354 + /// </param>
183.355 + protected internal override void SetDefaultValues(PlotModel model)
183.356 + {
183.357 + if (this.Color == null)
183.358 + {
183.359 + this.LineStyle = model.GetDefaultLineStyle();
183.360 + this.defaultColor = model.GetDefaultColor();
183.361 + }
183.362 + }
183.363 +
183.364 + /// <summary>
183.365 + /// Updates the max/min from the datapoints.
183.366 + /// </summary>
183.367 + protected internal override void UpdateMaxMin()
183.368 + {
183.369 + this.MinX = this.ColumnCoordinates.Min();
183.370 + this.MaxX = this.ColumnCoordinates.Max();
183.371 + this.MinY = this.RowCoordinates.Min();
183.372 + this.MaxY = this.RowCoordinates.Max();
183.373 + }
183.374 +
183.375 + /// <summary>
183.376 + /// Determines if two values are close.
183.377 + /// </summary>
183.378 + /// <param name="x1">
183.379 + /// The first value.
183.380 + /// </param>
183.381 + /// <param name="x2">
183.382 + /// The second value.
183.383 + /// </param>
183.384 + /// <param name="eps">
183.385 + /// The squared tolerance.
183.386 + /// </param>
183.387 + /// <returns>
183.388 + /// True if the values are close.
183.389 + /// </returns>
183.390 + private static bool AreClose(double x1, double x2, double eps = 1e-6)
183.391 + {
183.392 + double dx = x1 - x2;
183.393 + return dx * dx < eps;
183.394 + }
183.395 +
183.396 + /// <summary>
183.397 + /// Determines if two points are close.
183.398 + /// </summary>
183.399 + /// <param name="p0">
183.400 + /// The first point.
183.401 + /// </param>
183.402 + /// <param name="p1">
183.403 + /// The second point.
183.404 + /// </param>
183.405 + /// <param name="eps">
183.406 + /// The squared tolerance.
183.407 + /// </param>
183.408 + /// <returns>
183.409 + /// True if the points are close.
183.410 + /// </returns>
183.411 + private static bool AreClose(DataPoint p0, DataPoint p1, double eps = 1e-6)
183.412 + {
183.413 + double dx = p0.X - p1.X;
183.414 + double dy = p0.Y - p1.Y;
183.415 + return (dx * dx) + (dy * dy) < eps;
183.416 + }
183.417 +
183.418 + /// <summary>
183.419 + /// Gets the index of item that is closest to the specified value.
183.420 + /// </summary>
183.421 + /// <param name="values">A list of values.</param>
183.422 + /// <param name="value">A value.</param>
183.423 + /// <returns>An index.</returns>
183.424 + private static int IndexOf(IList<double> values, double value)
183.425 + {
183.426 + double min = double.MaxValue;
183.427 + int index = -1;
183.428 + for (int i = 0; i < values.Count; i++)
183.429 + {
183.430 + var d = Math.Abs(values[i] - value);
183.431 + if (d < min)
183.432 + {
183.433 + min = d;
183.434 + index = i;
183.435 + }
183.436 + }
183.437 +
183.438 + return index;
183.439 + }
183.440 +
183.441 + /// <summary>
183.442 + /// The add contour labels.
183.443 + /// </summary>
183.444 + /// <param name="contour">
183.445 + /// The contour.
183.446 + /// </param>
183.447 + /// <param name="pts">
183.448 + /// The pts.
183.449 + /// </param>
183.450 + /// <param name="clippingRect">
183.451 + /// The clipping rect.
183.452 + /// </param>
183.453 + /// <param name="contourLabels">
183.454 + /// The contour labels.
183.455 + /// </param>
183.456 + private void AddContourLabels(
183.457 + Contour contour, ScreenPoint[] pts, OxyRect clippingRect, List<ContourLabel> contourLabels)
183.458 + {
183.459 + // todo: support label spacing and label step
183.460 + if (pts.Length < 2)
183.461 + {
183.462 + return;
183.463 + }
183.464 +
183.465 + // Calculate position and angle of the label
183.466 + double i = (pts.Length - 1) * 0.5;
183.467 + var i0 = (int)i;
183.468 + int i1 = i0 + 1;
183.469 + double dx = pts[i1].X - pts[i0].X;
183.470 + double dy = pts[i1].Y - pts[i0].Y;
183.471 + double x = pts[i0].X + (dx * (i - i0));
183.472 + double y = pts[i0].Y + (dy * (i - i0));
183.473 + if (!clippingRect.Contains(x, y))
183.474 + {
183.475 + return;
183.476 + }
183.477 +
183.478 + var pos = new ScreenPoint(x, y);
183.479 + double angle = Math.Atan2(dy, dx) * 180 / Math.PI;
183.480 + if (angle > 90)
183.481 + {
183.482 + angle -= 180;
183.483 + }
183.484 +
183.485 + if (angle < -90)
183.486 + {
183.487 + angle += 180;
183.488 + }
183.489 +
183.490 + string text = contour.ContourLevel.ToString(this.LabelFormatString, this.ActualCulture);
183.491 + contourLabels.Add(new ContourLabel { Position = pos, Angle = angle, Text = text });
183.492 + }
183.493 +
183.494 + /// <summary>
183.495 + /// Finds the connected segment.
183.496 + /// </summary>
183.497 + /// <param name="point">
183.498 + /// The point.
183.499 + /// </param>
183.500 + /// <param name="contourLevel">
183.501 + /// The contour level.
183.502 + /// </param>
183.503 + /// <param name="eps">
183.504 + /// The eps.
183.505 + /// </param>
183.506 + /// <param name="reverse">
183.507 + /// reverse the segment if set to <c>true</c>.
183.508 + /// </param>
183.509 + /// <returns>
183.510 + /// The connected segment, or null if no segment was found.
183.511 + /// </returns>
183.512 + private ContourSegment FindConnectedSegment(DataPoint point, double contourLevel, double eps, out bool reverse)
183.513 + {
183.514 + reverse = false;
183.515 + foreach (var s in this.segments)
183.516 + {
183.517 + if (!AreClose(s.ContourLevel, contourLevel, eps))
183.518 + {
183.519 + continue;
183.520 + }
183.521 +
183.522 + if (AreClose(point, s.StartPoint, eps))
183.523 + {
183.524 + return s;
183.525 + }
183.526 +
183.527 + if (AreClose(point, s.EndPoint, eps))
183.528 + {
183.529 + reverse = true;
183.530 + return s;
183.531 + }
183.532 + }
183.533 +
183.534 + return null;
183.535 + }
183.536 +
183.537 + /// <summary>
183.538 + /// Joins the contour segments.
183.539 + /// </summary>
183.540 + /// <param name="eps">
183.541 + /// The tolerance for segment ends to connect (squared distance).
183.542 + /// </param>
183.543 + private void JoinContourSegments(double eps = 1e-10)
183.544 + {
183.545 + // This is a simple, slow, naïve method - should be improved:
183.546 + // http://stackoverflow.com/questions/1436091/joining-unordered-line-segments
183.547 + this.contours = new List<Contour>();
183.548 + var contourPoints = new List<IDataPoint>();
183.549 + int contourPointsCount = 0;
183.550 +
183.551 + ContourSegment firstSegment = null;
183.552 + int segmentCount = this.segments.Count;
183.553 + while (segmentCount > 0)
183.554 + {
183.555 + ContourSegment segment1 = null, segment2 = null;
183.556 +
183.557 + if (firstSegment != null)
183.558 + {
183.559 + bool reverse;
183.560 +
183.561 + // Find a segment that is connected to the head of the contour
183.562 + segment1 = this.FindConnectedSegment(
183.563 + (DataPoint)contourPoints[0], firstSegment.ContourLevel, eps, out reverse);
183.564 + if (segment1 != null)
183.565 + {
183.566 + contourPoints.Insert(0, reverse ? segment1.StartPoint : segment1.EndPoint);
183.567 + contourPointsCount++;
183.568 + this.segments.Remove(segment1);
183.569 + segmentCount--;
183.570 + }
183.571 +
183.572 + // Find a segment that is connected to the tail of the contour
183.573 + segment2 = this.FindConnectedSegment(
183.574 + (DataPoint)contourPoints[contourPointsCount - 1], firstSegment.ContourLevel, eps, out reverse);
183.575 + if (segment2 != null)
183.576 + {
183.577 + contourPoints.Add(reverse ? segment2.StartPoint : segment2.EndPoint);
183.578 + contourPointsCount++;
183.579 + this.segments.Remove(segment2);
183.580 + segmentCount--;
183.581 + }
183.582 + }
183.583 +
183.584 + if ((segment1 == null && segment2 == null) || segmentCount == 0)
183.585 + {
183.586 + if (contourPointsCount > 0 && firstSegment != null)
183.587 + {
183.588 + this.contours.Add(new Contour(contourPoints, firstSegment.ContourLevel));
183.589 + contourPoints = new List<IDataPoint>();
183.590 + contourPointsCount = 0;
183.591 + }
183.592 +
183.593 + if (segmentCount > 0)
183.594 + {
183.595 + firstSegment = this.segments.First();
183.596 + contourPoints.Add(firstSegment.StartPoint);
183.597 + contourPoints.Add(firstSegment.EndPoint);
183.598 + contourPointsCount += 2;
183.599 + this.segments.Remove(firstSegment);
183.600 + segmentCount--;
183.601 + }
183.602 + }
183.603 + }
183.604 + }
183.605 +
183.606 + /// <summary>
183.607 + /// Renders the contour label.
183.608 + /// </summary>
183.609 + /// <param name="rc">
183.610 + /// The render context.
183.611 + /// </param>
183.612 + /// <param name="cl">
183.613 + /// The contour label.
183.614 + /// </param>
183.615 + private void RenderLabel(IRenderContext rc, ContourLabel cl)
183.616 + {
183.617 + if (this.ActualFontSize > 0)
183.618 + {
183.619 + rc.DrawText(
183.620 + cl.Position,
183.621 + cl.Text,
183.622 + this.ActualTextColor,
183.623 + this.ActualFont,
183.624 + this.ActualFontSize,
183.625 + this.ActualFontWeight,
183.626 + cl.Angle,
183.627 + HorizontalAlignment.Center,
183.628 + VerticalAlignment.Middle);
183.629 + }
183.630 + }
183.631 +
183.632 + /// <summary>
183.633 + /// Renders the contour label background.
183.634 + /// </summary>
183.635 + /// <param name="rc">
183.636 + /// The render context.
183.637 + /// </param>
183.638 + /// <param name="cl">
183.639 + /// The contour label.
183.640 + /// </param>
183.641 + private void RenderLabelBackground(IRenderContext rc, ContourLabel cl)
183.642 + {
183.643 + if (this.LabelBackground != null)
183.644 + {
183.645 + // Calculate background polygon
183.646 + var size = rc.MeasureText(cl.Text, this.ActualFont, this.ActualFontSize, this.ActualFontWeight);
183.647 + double a = cl.Angle / 180 * Math.PI;
183.648 + double dx = Math.Cos(a);
183.649 + double dy = Math.Sin(a);
183.650 +
183.651 + double ux = dx * 0.6;
183.652 + double uy = dy * 0.6;
183.653 + double vx = -dy * 0.5;
183.654 + double vy = dx * 0.5;
183.655 + double x = cl.Position.X;
183.656 + double y = cl.Position.Y;
183.657 +
183.658 + var bpts = new[]
183.659 + {
183.660 + new ScreenPoint(x - (size.Width * ux) - (size.Height * vx), y - (size.Width * uy) - (size.Height * vy)),
183.661 + new ScreenPoint(x + (size.Width * ux) - (size.Height * vx), y + (size.Width * uy) - (size.Height * vy)),
183.662 + new ScreenPoint(x + (size.Width * ux) + (size.Height * vx), y + (size.Width * uy) + (size.Height * vy)),
183.663 + new ScreenPoint(x - (size.Width * ux) + (size.Height * vx), y - (size.Width * uy) + (size.Height * vy))
183.664 + };
183.665 + rc.DrawPolygon(bpts, this.LabelBackground, null);
183.666 + }
183.667 + }
183.668 +
183.669 + /// <summary>
183.670 + /// Represents a contour.
183.671 + /// </summary>
183.672 + private class Contour
183.673 + {
183.674 + /// <summary>
183.675 + /// Gets or sets the contour level.
183.676 + /// </summary>
183.677 + /// <value>The contour level.</value>
183.678 + internal readonly double ContourLevel;
183.679 +
183.680 + /// <summary>
183.681 + /// Gets or sets the points.
183.682 + /// </summary>
183.683 + /// <value>The points.</value>
183.684 + internal readonly IList<IDataPoint> Points;
183.685 +
183.686 + /// <summary>
183.687 + /// Initializes a new instance of the <see cref="Contour"/> class.
183.688 + /// </summary>
183.689 + /// <param name="points">
183.690 + /// The points.
183.691 + /// </param>
183.692 + /// <param name="contourLevel">
183.693 + /// The contour level.
183.694 + /// </param>
183.695 + public Contour(IList<IDataPoint> points, double contourLevel)
183.696 + {
183.697 + this.Points = points;
183.698 + this.ContourLevel = contourLevel;
183.699 + }
183.700 +
183.701 + /// <summary>
183.702 + /// Gets or sets the color of the contour.
183.703 + /// </summary>
183.704 + public OxyColor Color { get; set; }
183.705 + }
183.706 +
183.707 + /// <summary>
183.708 + /// Represents a contour label.
183.709 + /// </summary>
183.710 + private class ContourLabel
183.711 + {
183.712 + /// <summary>
183.713 + /// Gets or sets the angle.
183.714 + /// </summary>
183.715 + /// <value>The angle.</value>
183.716 + public double Angle { get; set; }
183.717 +
183.718 + /// <summary>
183.719 + /// Gets or sets the position.
183.720 + /// </summary>
183.721 + /// <value>The position.</value>
183.722 + public ScreenPoint Position { get; set; }
183.723 +
183.724 + /// <summary>
183.725 + /// Gets or sets the text.
183.726 + /// </summary>
183.727 + /// <value>The text.</value>
183.728 + public string Text { get; set; }
183.729 +
183.730 + }
183.731 +
183.732 + /// <summary>
183.733 + /// Represents a contour segment.
183.734 + /// </summary>
183.735 + private class ContourSegment
183.736 + {
183.737 + /// <summary>
183.738 + /// The contour level.
183.739 + /// </summary>
183.740 + internal readonly double ContourLevel;
183.741 +
183.742 + /// <summary>
183.743 + /// The end point.
183.744 + /// </summary>
183.745 + internal readonly DataPoint EndPoint;
183.746 +
183.747 + /// <summary>
183.748 + /// The start point.
183.749 + /// </summary>
183.750 + internal readonly DataPoint StartPoint;
183.751 +
183.752 + /// <summary>
183.753 + /// Initializes a new instance of the <see cref="ContourSegment"/> class.
183.754 + /// </summary>
183.755 + /// <param name="startPoint">
183.756 + /// The start point.
183.757 + /// </param>
183.758 + /// <param name="endPoint">
183.759 + /// The end point.
183.760 + /// </param>
183.761 + /// <param name="contourLevel">
183.762 + /// The contour level.
183.763 + /// </param>
183.764 + public ContourSegment(DataPoint startPoint, DataPoint endPoint, double contourLevel)
183.765 + {
183.766 + this.ContourLevel = contourLevel;
183.767 + this.StartPoint = startPoint;
183.768 + this.EndPoint = endPoint;
183.769 + }
183.770 +
183.771 + }
183.772 + }
183.773 +}
183.774 \ No newline at end of file
184.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
184.2 +++ b/External/OxyPlot/OxyPlot/Series/DataPointSeries.cs Sat Jun 08 16:53:22 2013 +0000
184.3 @@ -0,0 +1,325 @@
184.4 +// --------------------------------------------------------------------------------------------------------------------
184.5 +// <copyright file="DataPointSeries.cs" company="OxyPlot">
184.6 +// The MIT License (MIT)
184.7 +//
184.8 +// Copyright (c) 2012 Oystein Bjorke
184.9 +//
184.10 +// Permission is hereby granted, free of charge, to any person obtaining a
184.11 +// copy of this software and associated documentation files (the
184.12 +// "Software"), to deal in the Software without restriction, including
184.13 +// without limitation the rights to use, copy, modify, merge, publish,
184.14 +// distribute, sublicense, and/or sell copies of the Software, and to
184.15 +// permit persons to whom the Software is furnished to do so, subject to
184.16 +// the following conditions:
184.17 +//
184.18 +// The above copyright notice and this permission notice shall be included
184.19 +// in all copies or substantial portions of the Software.
184.20 +//
184.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
184.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
184.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
184.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
184.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
184.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
184.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
184.28 +// </copyright>
184.29 +// <summary>
184.30 +// Base class for series that contain a collection of IDataPoints.
184.31 +// </summary>
184.32 +// --------------------------------------------------------------------------------------------------------------------
184.33 +namespace OxyPlot.Series
184.34 +{
184.35 + using System;
184.36 + using System.Collections;
184.37 + using System.Collections.Generic;
184.38 + using System.Reflection;
184.39 +
184.40 + /// <summary>
184.41 + /// Provides an abstract base class for series that contain a collection of <see cref="IDataPoint"/>s.
184.42 + /// </summary>
184.43 + public abstract class DataPointSeries : XYAxisSeries
184.44 + {
184.45 + /// <summary>
184.46 + /// The list of data points.
184.47 + /// </summary>
184.48 + private IList<IDataPoint> points = new List<IDataPoint>();
184.49 +
184.50 + /// <summary>
184.51 + /// Initializes a new instance of the <see cref = "DataPointSeries" /> class.
184.52 + /// </summary>
184.53 + protected DataPointSeries()
184.54 + {
184.55 + this.DataFieldX = null;
184.56 + this.DataFieldY = null;
184.57 + }
184.58 +
184.59 + /// <summary>
184.60 + /// Gets or sets a value indicating whether the tracker can interpolate points.
184.61 + /// </summary>
184.62 + public bool CanTrackerInterpolatePoints { get; set; }
184.63 +
184.64 + /// <summary>
184.65 + /// Gets or sets the data field X.
184.66 + /// </summary>
184.67 + /// <value>The data field X.</value>
184.68 + public string DataFieldX { get; set; }
184.69 +
184.70 + /// <summary>
184.71 + /// Gets or sets the data field Y.
184.72 + /// </summary>
184.73 + /// <value>The data field Y.</value>
184.74 + public string DataFieldY { get; set; }
184.75 +
184.76 + /// <summary>
184.77 + /// Gets or sets the mapping delegate.
184.78 + /// Example: series1.Mapping = item => new DataPoint(((MyType)item).Time,((MyType)item).Value);
184.79 + /// </summary>
184.80 + /// <value>The mapping.</value>
184.81 + public Func<object, IDataPoint> Mapping { get; set; }
184.82 +
184.83 + /// <summary>
184.84 + /// Gets or sets the points list.
184.85 + /// </summary>
184.86 + /// <value>The points list.</value>
184.87 + public IList<IDataPoint> Points
184.88 + {
184.89 + get
184.90 + {
184.91 + return this.points;
184.92 + }
184.93 +
184.94 + set
184.95 + {
184.96 + this.points = value;
184.97 + }
184.98 + }
184.99 +
184.100 + /// <summary>
184.101 + /// Gets or sets a value indicating whether this <see cref = "DataPointSeries" /> is smooth.
184.102 + /// </summary>
184.103 + /// <value><c>true</c> if smooth; otherwise, <c>false</c>.</value>
184.104 + public bool Smooth { get; set; }
184.105 +
184.106 + /// <summary>
184.107 + /// Gets the point on the series that is nearest the specified point.
184.108 + /// </summary>
184.109 + /// <param name="point">The point.</param>
184.110 + /// <param name="interpolate">Interpolate the series if this flag is set to <c>true</c>.</param>
184.111 + /// <returns>
184.112 + /// A TrackerHitResult for the current hit.
184.113 + /// </returns>
184.114 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
184.115 + {
184.116 + if (interpolate && !this.CanTrackerInterpolatePoints)
184.117 + {
184.118 + return null;
184.119 + }
184.120 +
184.121 + if (interpolate)
184.122 + {
184.123 + return this.GetNearestInterpolatedPointInternal(this.Points, point);
184.124 + }
184.125 +
184.126 + return this.GetNearestPointInternal(this.Points, point);
184.127 + }
184.128 +
184.129 + /// <summary>
184.130 + /// Gets the item at the specified index.
184.131 + /// </summary>
184.132 + /// <param name="i">The index of the item.</param>
184.133 + /// <returns>The item of the index.</returns>
184.134 + protected override object GetItem(int i)
184.135 + {
184.136 + if (this.ItemsSource == null && this.Points != null && i < this.Points.Count)
184.137 + {
184.138 + return this.Points[i];
184.139 + }
184.140 +
184.141 + return base.GetItem(i);
184.142 + }
184.143 +
184.144 + /// <summary>
184.145 + /// The update data.
184.146 + /// </summary>
184.147 + protected internal override void UpdateData()
184.148 + {
184.149 + if (this.ItemsSource == null)
184.150 + {
184.151 + return;
184.152 + }
184.153 +
184.154 + this.AddDataPoints(this.Points);
184.155 + }
184.156 +
184.157 + /// <summary>
184.158 + /// Updates the max/min from the datapoints.
184.159 + /// </summary>
184.160 + protected internal override void UpdateMaxMin()
184.161 + {
184.162 + base.UpdateMaxMin();
184.163 + this.InternalUpdateMaxMin(this.Points);
184.164 + }
184.165 +
184.166 + /// <summary>
184.167 + /// The add data points.
184.168 + /// </summary>
184.169 + /// <param name="pts">
184.170 + /// The points.
184.171 + /// </param>
184.172 + protected void AddDataPoints(IList<IDataPoint> pts)
184.173 + {
184.174 + pts.Clear();
184.175 +
184.176 + // Use the mapping to generate the points
184.177 + if (this.Mapping != null)
184.178 + {
184.179 + foreach (var item in this.ItemsSource)
184.180 + {
184.181 + pts.Add(this.Mapping(item));
184.182 + }
184.183 +
184.184 + return;
184.185 + }
184.186 +
184.187 + // Get DataPoints from the items in ItemsSource
184.188 + // if they implement IDataPointProvider
184.189 + // If DataFields are set, this is not used
184.190 + if (this.DataFieldX == null || this.DataFieldY == null)
184.191 + {
184.192 + foreach (var item in this.ItemsSource)
184.193 + {
184.194 + var dp = item as IDataPoint;
184.195 + if (dp != null)
184.196 + {
184.197 + pts.Add(dp);
184.198 + continue;
184.199 + }
184.200 +
184.201 + var idpp = item as IDataPointProvider;
184.202 + if (idpp == null)
184.203 + {
184.204 + continue;
184.205 + }
184.206 +
184.207 + pts.Add(idpp.GetDataPoint());
184.208 + }
184.209 + }
184.210 + else
184.211 + {
184.212 + // TODO: is there a better way to do this?
184.213 + // http://msdn.microsoft.com/en-us/library/bb613546.aspx
184.214 +
184.215 + // Using reflection on DataFieldX and DataFieldY
184.216 + this.AddDataPoints((IList)pts, this.ItemsSource, this.DataFieldX, this.DataFieldY);
184.217 + }
184.218 + }
184.219 +
184.220 + /// <summary>
184.221 + /// The add data points.
184.222 + /// </summary>
184.223 + /// <param name="dest">
184.224 + /// The dest.
184.225 + /// </param>
184.226 + /// <param name="itemsSource">
184.227 + /// The items source.
184.228 + /// </param>
184.229 + /// <param name="dataFieldX">
184.230 + /// The data field x.
184.231 + /// </param>
184.232 + /// <param name="dataFieldY">
184.233 + /// The data field y.
184.234 + /// </param>
184.235 + protected void AddDataPoints(IList dest, IEnumerable itemsSource, string dataFieldX, string dataFieldY)
184.236 + {
184.237 + PropertyInfo pix = null;
184.238 + PropertyInfo piy = null;
184.239 + Type t = null;
184.240 +
184.241 + foreach (var o in itemsSource)
184.242 + {
184.243 + if (pix == null || o.GetType() != t)
184.244 + {
184.245 + t = o.GetType();
184.246 + pix = t.GetProperty(dataFieldX);
184.247 + piy = t.GetProperty(dataFieldY);
184.248 + if (pix == null)
184.249 + {
184.250 + throw new InvalidOperationException(
184.251 + string.Format("Could not find data field {0} on type {1}", this.DataFieldX, t));
184.252 + }
184.253 +
184.254 + if (piy == null)
184.255 + {
184.256 + throw new InvalidOperationException(
184.257 + string.Format("Could not find data field {0} on type {1}", this.DataFieldY, t));
184.258 + }
184.259 + }
184.260 +
184.261 + double x = this.ToDouble(pix.GetValue(o, null));
184.262 + double y = this.ToDouble(piy.GetValue(o, null));
184.263 +
184.264 + var pp = new DataPoint(x, y);
184.265 + dest.Add(pp);
184.266 + }
184.267 +
184.268 + //var filler = new ListFiller<DataPoint>();
184.269 + //filler.Add(dataFieldX, (item, value) => item.X = this.ToDouble(value));
184.270 + //filler.Add(dataFieldY, (item, value) => item.Y = this.ToDouble(value));
184.271 + //filler.Fill(dest, itemsSource);
184.272 + }
184.273 +
184.274 + /// <summary>
184.275 + /// Updates the Max/Min limits from the specified point list.
184.276 + /// </summary>
184.277 + /// <param name="pts">
184.278 + /// The points.
184.279 + /// </param>
184.280 + protected void InternalUpdateMaxMin(IList<IDataPoint> pts)
184.281 + {
184.282 + if (pts == null || pts.Count == 0)
184.283 + {
184.284 + return;
184.285 + }
184.286 +
184.287 + double minx = this.MinX;
184.288 + double miny = this.MinY;
184.289 + double maxx = this.MaxX;
184.290 + double maxy = this.MaxY;
184.291 +
184.292 + foreach (var pt in pts)
184.293 + {
184.294 + if (!this.IsValidPoint(pt, this.XAxis, this.YAxis))
184.295 + {
184.296 + continue;
184.297 + }
184.298 +
184.299 + double x = pt.X;
184.300 + double y = pt.Y;
184.301 + if (x < minx || double.IsNaN(minx))
184.302 + {
184.303 + minx = x;
184.304 + }
184.305 +
184.306 + if (x > maxx || double.IsNaN(maxx))
184.307 + {
184.308 + maxx = x;
184.309 + }
184.310 +
184.311 + if (y < miny || double.IsNaN(miny))
184.312 + {
184.313 + miny = y;
184.314 + }
184.315 +
184.316 + if (y > maxy || double.IsNaN(maxy))
184.317 + {
184.318 + maxy = y;
184.319 + }
184.320 + }
184.321 +
184.322 + this.MinX = minx;
184.323 + this.MinY = miny;
184.324 + this.MaxX = maxx;
184.325 + this.MaxY = maxy;
184.326 + }
184.327 + }
184.328 +}
184.329 \ No newline at end of file
185.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
185.2 +++ b/External/OxyPlot/OxyPlot/Series/DataSeries.cs Sat Jun 08 16:53:22 2013 +0000
185.3 @@ -0,0 +1,391 @@
185.4 +// --------------------------------------------------------------------------------------------------------------------
185.5 +// <copyright file="DataSeries.cs" company="OxyPlot">
185.6 +// The MIT License (MIT)
185.7 +//
185.8 +// Copyright (c) 2012 Oystein Bjorke
185.9 +//
185.10 +// Permission is hereby granted, free of charge, to any person obtaining a
185.11 +// copy of this software and associated documentation files (the
185.12 +// "Software"), to deal in the Software without restriction, including
185.13 +// without limitation the rights to use, copy, modify, merge, publish,
185.14 +// distribute, sublicense, and/or sell copies of the Software, and to
185.15 +// permit persons to whom the Software is furnished to do so, subject to
185.16 +// the following conditions:
185.17 +//
185.18 +// The above copyright notice and this permission notice shall be included
185.19 +// in all copies or substantial portions of the Software.
185.20 +//
185.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
185.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
185.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
185.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
185.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
185.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
185.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
185.28 +// </copyright>
185.29 +// <summary>
185.30 +// DataPointProvider interface.
185.31 +// </summary>
185.32 +// --------------------------------------------------------------------------------------------------------------------
185.33 +using System;
185.34 +using System.Collections;
185.35 +using System.Collections.Generic;
185.36 +using System.Collections.ObjectModel;
185.37 +using System.ComponentModel;
185.38 +using System.Linq;
185.39 +using System.Reflection;
185.40 +
185.41 +namespace OxyPlot
185.42 +{
185.43 + /// <summary>
185.44 + /// DataPointProvider interface.
185.45 + /// </summary>
185.46 + public interface IDataPointProvider
185.47 + {
185.48 + /// <summary>
185.49 + /// Gets the data point.
185.50 + /// </summary>
185.51 + /// <returns></returns>
185.52 + DataPoint GetDataPoint();
185.53 + }
185.54 +
185.55 + public abstract class DataSeries : PlotSeriesBase
185.56 + {
185.57 + protected IList<DataPoint> points;
185.58 +
185.59 + protected DataSeries()
185.60 + {
185.61 + points = new Collection<DataPoint>();
185.62 + DataFieldX = "X";
185.63 + DataFieldY = "Y";
185.64 + CanTrackerInterpolatePoints = false;
185.65 + }
185.66 +
185.67 + /// <summary>
185.68 + /// Gets or sets the items source.
185.69 + /// </summary>
185.70 + /// <value>The items source.</value>
185.71 + public IEnumerable ItemsSource { get; set; }
185.72 +
185.73 + /// <summary>
185.74 + /// Gets or sets the data field X.
185.75 + /// </summary>
185.76 + /// <value>The data field X.</value>
185.77 + public string DataFieldX { get; set; }
185.78 +
185.79 + /// <summary>
185.80 + /// Gets or sets the data field Y.
185.81 + /// </summary>
185.82 + /// <value>The data field Y.</value>
185.83 + public string DataFieldY { get; set; }
185.84 +
185.85 + /// <summary>
185.86 + /// Gets or sets the mapping deleagte.
185.87 + /// Example: series1.Mapping = item => new DataPoint(((MyType)item).Time,((MyType)item).Value);
185.88 + /// </summary>
185.89 + /// <value>The mapping.</value>
185.90 + public Func<object, DataPoint> Mapping { get; set; }
185.91 +
185.92 + /// <summary>
185.93 + /// Gets or sets the points.
185.94 + /// </summary>
185.95 + /// <value>The points.</value>
185.96 + [Browsable(false)]
185.97 + public IList<DataPoint> Points
185.98 + {
185.99 + get { return points; }
185.100 + set { points = value; }
185.101 + }
185.102 +
185.103 + /// <summary>
185.104 + /// Gets or sets a value indicating whether this <see cref = "DataSeries" /> is smooth.
185.105 + /// </summary>
185.106 + /// <value><c>true</c> if smooth; otherwise, <c>false</c>.</value>
185.107 + public bool Smooth { get; set; }
185.108 +
185.109 + public override void UpdateData()
185.110 + {
185.111 + if (ItemsSource == null)
185.112 + {
185.113 + return;
185.114 + }
185.115 +
185.116 + points.Clear();
185.117 +
185.118 + // Use the mapping to generate the points
185.119 + if (Mapping != null)
185.120 + {
185.121 + foreach (var item in ItemsSource)
185.122 + {
185.123 + points.Add(Mapping(item));
185.124 + }
185.125 + }
185.126 +
185.127 + // Get DataPoints from the items in ItemsSource
185.128 + // if they implement IDataPointProvider
185.129 + // If DataFields are set, this is not used
185.130 + if (DataFieldX == null || DataFieldY == null)
185.131 + {
185.132 + foreach (var item in ItemsSource)
185.133 + {
185.134 + var idpp = item as IDataPointProvider;
185.135 + if (idpp == null)
185.136 + {
185.137 + continue;
185.138 + }
185.139 +
185.140 + points.Add(idpp.GetDataPoint());
185.141 + }
185.142 +
185.143 + return;
185.144 + }
185.145 +
185.146 + // TODO: is there a better way to do this?
185.147 + // http://msdn.microsoft.com/en-us/library/bb613546.aspx
185.148 +
185.149 + // Using reflection on DataFieldX and DataFieldY
185.150 + AddDataPoints(points, ItemsSource, DataFieldX, DataFieldY);
185.151 + }
185.152 +
185.153 + /// <summary>
185.154 + /// Converts the value of the specified object to a double precision floating point number.
185.155 + /// DateTime objects are converted using DateTimeAxis.ToDouble
185.156 + /// TimeSpan objects are converted using TimeSpanAxis.ToDouble
185.157 + /// </summary>
185.158 + /// <param name="value">The value.</param>
185.159 + /// <returns></returns>
185.160 + protected virtual double ToDouble(object value)
185.161 + {
185.162 + if (value is DateTime)
185.163 + {
185.164 + return DateTimeAxis.ToDouble((DateTime)value);
185.165 + }
185.166 +
185.167 + if (value is TimeSpan)
185.168 + {
185.169 + return ((TimeSpan)value).TotalSeconds;
185.170 + }
185.171 +
185.172 + return Convert.ToDouble(value);
185.173 + }
185.174 +
185.175 + /// <summary>
185.176 + /// Updates the max/min from the datapoints.
185.177 + /// </summary>
185.178 + public override void UpdateMaxMin()
185.179 + {
185.180 + base.UpdateMaxMin();
185.181 + InternalUpdateMaxMin(points);
185.182 + }
185.183 +
185.184 + /// <summary>
185.185 + /// Gets the point in the dataset that is nearest the specified point.
185.186 + /// </summary>
185.187 + /// <param name = "point">The point.</param>
185.188 + /// <param name = "dpn">The nearest point (data coordinates).</param>
185.189 + /// <param name = "spn">The nearest point (screen coordinates).</param>
185.190 + /// <returns></returns>
185.191 + public override bool GetNearestPoint(ScreenPoint point, out DataPoint dpn, out ScreenPoint spn)
185.192 + {
185.193 + spn = default(ScreenPoint);
185.194 + dpn = default(DataPoint);
185.195 +
185.196 + double minimumDistance = double.MaxValue;
185.197 + foreach (var p in points)
185.198 + {
185.199 + var sp = AxisBase.Transform(p, XAxis, YAxis);
185.200 + double dx = sp.x - point.x;
185.201 + double dy = sp.y - point.y;
185.202 + double d2 = dx * dx + dy * dy;
185.203 +
185.204 + if (d2 < minimumDistance)
185.205 + {
185.206 + dpn = p;
185.207 + spn = sp;
185.208 + minimumDistance = d2;
185.209 + }
185.210 + }
185.211 +
185.212 + return minimumDistance < double.MaxValue;
185.213 + }
185.214 +
185.215 + /// <summary>
185.216 + /// Gets the point on the curve that is nearest the specified point.
185.217 + /// </summary>
185.218 + /// <param name = "point">The point.</param>
185.219 + /// <param name = "dpn">The nearest point (data coordinates).</param>
185.220 + /// <param name = "spn">The nearest point (screen coordinates).</param>
185.221 + /// <returns></returns>
185.222 + public override bool GetNearestInterpolatedPoint(ScreenPoint point, out DataPoint dpn, out ScreenPoint spn)
185.223 + {
185.224 + spn = default(ScreenPoint);
185.225 + dpn = default(DataPoint);
185.226 +
185.227 + // http://local.wasp.uwa.edu.au/~pbourke/geometry/pointline/
185.228 + double minimumDistance = double.MaxValue;
185.229 +
185.230 + for (int i = 0; i + 1 < points.Count; i++)
185.231 + {
185.232 + var p1 = points[i];
185.233 + var p2 = points[i + 1];
185.234 + var sp1 = AxisBase.Transform(p1, XAxis, YAxis);
185.235 + var sp2 = AxisBase.Transform(p2, XAxis, YAxis);
185.236 +
185.237 + double sp21X = sp2.x - sp1.x;
185.238 + double sp21Y = sp2.y - sp1.y;
185.239 + double u1 = (point.x - sp1.x) * sp21X + (point.y - sp1.y) * sp21Y;
185.240 + double u2 = sp21X * sp21X + sp21Y * sp21Y;
185.241 + double ds = sp21X * sp21X + sp21Y * sp21Y;
185.242 +
185.243 + if (ds < 4)
185.244 + {
185.245 + // if the points are very close, we can get numerical problems, just use the first point...
185.246 + u1 = 0; u2 = 1;
185.247 + }
185.248 +
185.249 + if (u2 == 0)
185.250 + {
185.251 + continue; // P1 && P2 coincident
185.252 + }
185.253 +
185.254 + double u = u1 / u2;
185.255 + if (u < 0 || u > 1)
185.256 + {
185.257 + continue; // outside line
185.258 + }
185.259 +
185.260 + double sx = sp1.x + u * sp21X;
185.261 + double sy = sp1.y + u * sp21Y;
185.262 +
185.263 + double dx = point.x - sx;
185.264 + double dy = point.y - sy;
185.265 + double distance = dx * dx + dy * dy;
185.266 +
185.267 + if (distance < minimumDistance)
185.268 + {
185.269 + double px = p1.x + u * (p2.x - p1.x);
185.270 + double py = p1.y + u * (p2.y - p1.y);
185.271 + dpn = new DataPoint(px, py);
185.272 + spn = new ScreenPoint(sx, sy);
185.273 + minimumDistance = distance;
185.274 + }
185.275 + }
185.276 +
185.277 + return minimumDistance < double.MaxValue;
185.278 + }
185.279 +
185.280 + protected void AddDataPoints(ICollection<DataPoint> points, IEnumerable itemsSource, string dataFieldX, string dataFieldY)
185.281 + {
185.282 + PropertyInfo pix = null;
185.283 + PropertyInfo piy = null;
185.284 + Type t = null;
185.285 +
185.286 + foreach (var o in itemsSource)
185.287 + {
185.288 + if (pix == null || o.GetType() != t)
185.289 + {
185.290 + t = o.GetType();
185.291 + pix = t.GetProperty(dataFieldX);
185.292 + piy = t.GetProperty(dataFieldY);
185.293 + if (pix == null)
185.294 + {
185.295 + throw new InvalidOperationException(string.Format("Could not find data field {0} on type {1}",
185.296 + DataFieldX, t));
185.297 + }
185.298 +
185.299 + if (piy == null)
185.300 + {
185.301 + throw new InvalidOperationException(string.Format("Could not find data field {0} on type {1}",
185.302 + DataFieldY, t));
185.303 + }
185.304 + }
185.305 +
185.306 + var x = ToDouble(pix.GetValue(o, null));
185.307 + var y = ToDouble(piy.GetValue(o, null));
185.308 +
185.309 + var pp = new DataPoint(x, y);
185.310 + points.Add(pp);
185.311 + }
185.312 + }
185.313 +
185.314 + /// <summary>
185.315 + /// Updates the Max/Min limits from the specified point list.
185.316 + /// </summary>
185.317 + /// <param name="pts">The PTS.</param>
185.318 + protected void InternalUpdateMaxMin(IList<DataPoint> pts)
185.319 + {
185.320 + if (pts == null || pts.Count == 0)
185.321 + {
185.322 + return;
185.323 + }
185.324 +
185.325 + double minx = MinX;
185.326 + double miny = MinY;
185.327 + double maxx = MaxX;
185.328 + double maxy = MaxY;
185.329 +
185.330 + foreach (var pt in pts)
185.331 + {
185.332 + if (!IsValidPoint(pt,XAxis,YAxis))
185.333 + continue;
185.334 + if (pt.x < minx || double.IsNaN(minx)) minx = pt.x;
185.335 + if (pt.x > maxx || double.IsNaN(maxx)) maxx = pt.x;
185.336 + if (pt.y < miny || double.IsNaN(miny)) miny = pt.y;
185.337 + if (pt.y > maxy || double.IsNaN(maxy)) maxy = pt.y;
185.338 + }
185.339 +
185.340 + MinX = minx;
185.341 + MinY = miny;
185.342 + MaxX = maxx;
185.343 + MaxY = maxy;
185.344 +
185.345 + XAxis.Include(MinX);
185.346 + XAxis.Include(MaxX);
185.347 + YAxis.Include(MinY);
185.348 + YAxis.Include(MaxY);
185.349 + }
185.350 +
185.351 + /// <summary>
185.352 + /// Gets the value from the specified X.
185.353 + /// </summary>
185.354 + /// <param name = "x">The x.</param>
185.355 + /// <returns></returns>
185.356 + public double? GetValueFromX(double x)
185.357 + {
185.358 + for (int i = 0; i + 1 < points.Count; i++)
185.359 + {
185.360 + if (IsBetween(x, points[i].x, points[i + 1].x))
185.361 + {
185.362 + return points[i].y +
185.363 + (points[i + 1].y - points[i].y) /
185.364 + (points[i + 1].x - points[i].x) * (x - points[i].x);
185.365 + }
185.366 + }
185.367 +
185.368 + return null;
185.369 + }
185.370 +
185.371 + private static bool IsBetween(double x, double x0, double x1)
185.372 + {
185.373 + if (x >= x0 && x <= x1)
185.374 + {
185.375 + return true;
185.376 + }
185.377 +
185.378 + if (x >= x1 && x <= x0)
185.379 + {
185.380 + return true;
185.381 + }
185.382 +
185.383 + return false;
185.384 + }
185.385 +
185.386 + public virtual bool IsValidPoint(DataPoint pt, IAxis xAxis, IAxis yAxis)
185.387 + {
185.388 + return !double.IsNaN(pt.X) && !double.IsInfinity(pt.X)
185.389 + && !double.IsNaN(pt.Y) && !double.IsInfinity(pt.Y)
185.390 + && (xAxis!=null && xAxis.IsValidValue(pt.X))
185.391 + && (yAxis!=null && yAxis.IsValidValue(pt.Y));
185.392 + }
185.393 + }
185.394 +}
185.395 \ No newline at end of file
186.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
186.2 +++ b/External/OxyPlot/OxyPlot/Series/FunctionSeries.cs Sat Jun 08 16:53:22 2013 +0000
186.3 @@ -0,0 +1,157 @@
186.4 +// --------------------------------------------------------------------------------------------------------------------
186.5 +// <copyright file="FunctionSeries.cs" company="OxyPlot">
186.6 +// The MIT License (MIT)
186.7 +//
186.8 +// Copyright (c) 2012 Oystein Bjorke
186.9 +//
186.10 +// Permission is hereby granted, free of charge, to any person obtaining a
186.11 +// copy of this software and associated documentation files (the
186.12 +// "Software"), to deal in the Software without restriction, including
186.13 +// without limitation the rights to use, copy, modify, merge, publish,
186.14 +// distribute, sublicense, and/or sell copies of the Software, and to
186.15 +// permit persons to whom the Software is furnished to do so, subject to
186.16 +// the following conditions:
186.17 +//
186.18 +// The above copyright notice and this permission notice shall be included
186.19 +// in all copies or substantial portions of the Software.
186.20 +//
186.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
186.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
186.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
186.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
186.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
186.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
186.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
186.28 +// </copyright>
186.29 +// <summary>
186.30 +// Represents a line series that generates its dataset from a function.
186.31 +// </summary>
186.32 +// --------------------------------------------------------------------------------------------------------------------
186.33 +namespace OxyPlot.Series
186.34 +{
186.35 + using System;
186.36 +
186.37 + /// <summary>
186.38 + /// Represents a line series that generates its dataset from a function.
186.39 + /// </summary>
186.40 + /// <remarks>
186.41 + /// Define f(x) and make a plot on the range [x0,x1] or define fx(t) and fy(t) and make a plot on the range [t0,t1].
186.42 + /// </remarks>
186.43 + public class FunctionSeries : LineSeries
186.44 + {
186.45 + /// <summary>
186.46 + /// Initializes a new instance of the <see cref = "FunctionSeries" /> class.
186.47 + /// </summary>
186.48 + public FunctionSeries()
186.49 + {
186.50 + }
186.51 +
186.52 + /// <summary>
186.53 + /// Initializes a new instance of the <see cref="FunctionSeries"/> class.
186.54 + /// </summary>
186.55 + /// <param name="f">
186.56 + /// The function f(x).
186.57 + /// </param>
186.58 + /// <param name="x0">
186.59 + /// The start x value.
186.60 + /// </param>
186.61 + /// <param name="x1">
186.62 + /// The end x value.
186.63 + /// </param>
186.64 + /// <param name="dx">
186.65 + /// The increment in x.
186.66 + /// </param>
186.67 + /// <param name="title">
186.68 + /// The title (optional).
186.69 + /// </param>
186.70 + public FunctionSeries(Func<double, double> f, double x0, double x1, double dx, string title = null)
186.71 + {
186.72 + this.Title = title;
186.73 + for (double x = x0; x <= x1 + (dx * 0.5); x += dx)
186.74 + {
186.75 + this.Points.Add(new DataPoint(x, f(x)));
186.76 + }
186.77 + }
186.78 +
186.79 + /// <summary>
186.80 + /// Initializes a new instance of the <see cref="FunctionSeries"/> class.
186.81 + /// </summary>
186.82 + /// <param name="f">
186.83 + /// The function f(x).
186.84 + /// </param>
186.85 + /// <param name="x0">
186.86 + /// The start x value.
186.87 + /// </param>
186.88 + /// <param name="x1">
186.89 + /// The end x value.
186.90 + /// </param>
186.91 + /// <param name="n">
186.92 + /// The number of points.
186.93 + /// </param>
186.94 + /// <param name="title">
186.95 + /// The title (optional).
186.96 + /// </param>
186.97 + public FunctionSeries(Func<double, double> f, double x0, double x1, int n, string title = null)
186.98 + : this(f, x0, x1, (x1 - x0) / (n - 1), title)
186.99 + {
186.100 + }
186.101 +
186.102 + /// <summary>
186.103 + /// Initializes a new instance of the <see cref="FunctionSeries"/> class.
186.104 + /// </summary>
186.105 + /// <param name="fx">
186.106 + /// The function fx(t).
186.107 + /// </param>
186.108 + /// <param name="fy">
186.109 + /// The function fy(t).
186.110 + /// </param>
186.111 + /// <param name="t0">
186.112 + /// The t0.
186.113 + /// </param>
186.114 + /// <param name="t1">
186.115 + /// The t1.
186.116 + /// </param>
186.117 + /// <param name="dt">
186.118 + /// The increment dt.
186.119 + /// </param>
186.120 + /// <param name="title">
186.121 + /// The title.
186.122 + /// </param>
186.123 + public FunctionSeries(Func<double, double> fx, Func<double, double> fy, double t0, double t1, double dt, string title = null)
186.124 + {
186.125 + this.Title = title;
186.126 + for (double t = t0; t <= t1 + (dt * 0.5); t += dt)
186.127 + {
186.128 + this.Points.Add(new DataPoint(fx(t), fy(t)));
186.129 + }
186.130 + }
186.131 +
186.132 + /// <summary>
186.133 + /// Initializes a new instance of the <see cref="FunctionSeries"/> class.
186.134 + /// </summary>
186.135 + /// <param name="fx">
186.136 + /// The function fx(t).
186.137 + /// </param>
186.138 + /// <param name="fy">
186.139 + /// The function fy(t).
186.140 + /// </param>
186.141 + /// <param name="t0">
186.142 + /// The t0.
186.143 + /// </param>
186.144 + /// <param name="t1">
186.145 + /// The t1.
186.146 + /// </param>
186.147 + /// <param name="n">
186.148 + /// The number of points.
186.149 + /// </param>
186.150 + /// <param name="title">
186.151 + /// The title.
186.152 + /// </param>
186.153 + public FunctionSeries(
186.154 + Func<double, double> fx, Func<double, double> fy, double t0, double t1, int n, string title = null)
186.155 + : this(fx, fy, t0, t1, (t1 - t0) / (n - 1), title)
186.156 + {
186.157 + }
186.158 +
186.159 + }
186.160 +}
186.161 \ No newline at end of file
187.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
187.2 +++ b/External/OxyPlot/OxyPlot/Series/HeatMapSeries.cs Sat Jun 08 16:53:22 2013 +0000
187.3 @@ -0,0 +1,238 @@
187.4 +// --------------------------------------------------------------------------------------------------------------------
187.5 +// <copyright file="HeatMapSeries.cs" company="OxyPlot">
187.6 +// The MIT License (MIT)
187.7 +//
187.8 +// Copyright (c) 2012 Oystein Bjorke
187.9 +//
187.10 +// Permission is hereby granted, free of charge, to any person obtaining a
187.11 +// copy of this software and associated documentation files (the
187.12 +// "Software"), to deal in the Software without restriction, including
187.13 +// without limitation the rights to use, copy, modify, merge, publish,
187.14 +// distribute, sublicense, and/or sell copies of the Software, and to
187.15 +// permit persons to whom the Software is furnished to do so, subject to
187.16 +// the following conditions:
187.17 +//
187.18 +// The above copyright notice and this permission notice shall be included
187.19 +// in all copies or substantial portions of the Software.
187.20 +//
187.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
187.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
187.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
187.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
187.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
187.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
187.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
187.28 +// </copyright>
187.29 +// <summary>
187.30 +// The heat map series.
187.31 +// </summary>
187.32 +// --------------------------------------------------------------------------------------------------------------------
187.33 +
187.34 +namespace OxyPlot.Series
187.35 +{
187.36 + using System;
187.37 + using System.Collections.Generic;
187.38 + using System.Linq;
187.39 +
187.40 + using OxyPlot.Axes;
187.41 +
187.42 + /// <summary>
187.43 + /// The heat map series.
187.44 + /// </summary>
187.45 + /// <remarks>
187.46 + /// Does not work with Silverlight. Silverlight does not support bitmaps, only PNG and JPG.
187.47 + /// </remarks>
187.48 + public class HeatMapSeries : XYAxisSeries
187.49 + {
187.50 + /// <summary>
187.51 + /// The hash code of the current data.
187.52 + /// </summary>
187.53 + private int dataHash;
187.54 +
187.55 + /// <summary>
187.56 + /// The image
187.57 + /// </summary>
187.58 + private OxyImage image;
187.59 +
187.60 + /// <summary>
187.61 + /// Gets or sets the x 0.
187.62 + /// </summary>
187.63 + public double X0 { get; set; }
187.64 +
187.65 + /// <summary>
187.66 + /// Gets or sets the x 1.
187.67 + /// </summary>
187.68 + public double X1 { get; set; }
187.69 +
187.70 + /// <summary>
187.71 + /// Gets or sets the y 0.
187.72 + /// </summary>
187.73 + public double Y0 { get; set; }
187.74 +
187.75 + /// <summary>
187.76 + /// Gets or sets the y 1.
187.77 + /// </summary>
187.78 + public double Y1 { get; set; }
187.79 +
187.80 + /// <summary>
187.81 + /// Gets or sets the data.
187.82 + /// </summary>
187.83 + public double[,] Data { get; set; }
187.84 +
187.85 + /// <summary>
187.86 + /// Gets or sets the minimum value of the dataset.
187.87 + /// </summary>
187.88 + public double MinValue { get; protected set; }
187.89 +
187.90 + /// <summary>
187.91 + /// Gets or sets the maximum value of the dataset.
187.92 + /// </summary>
187.93 + public double MaxValue { get; protected set; }
187.94 +
187.95 + /// <summary>
187.96 + /// Gets or sets the color axis.
187.97 + /// </summary>
187.98 + /// <value>
187.99 + /// The color axis.
187.100 + /// </value>
187.101 + public ColorAxis ColorAxis { get; protected set; }
187.102 +
187.103 + /// <summary>
187.104 + /// Gets or sets the color axis key.
187.105 + /// </summary>
187.106 + /// <value> The color axis key. </value>
187.107 + public string ColorAxisKey { get; set; }
187.108 +
187.109 + /// <summary>
187.110 + /// Renders the series on the specified render context.
187.111 + /// </summary>
187.112 + /// <param name="rc">
187.113 + /// The rendering context.
187.114 + /// </param>
187.115 + /// <param name="model">
187.116 + /// The model.
187.117 + /// </param>
187.118 + public override void Render(IRenderContext rc, PlotModel model)
187.119 + {
187.120 + if (this.Data == null)
187.121 + {
187.122 + this.image = null;
187.123 + return;
187.124 + }
187.125 +
187.126 + int m = this.Data.GetLength(0);
187.127 + int n = this.Data.GetLength(1);
187.128 + double dx = (this.X1 - this.X0) / m;
187.129 + double left = this.X0 - (dx * 0.5);
187.130 + double right = this.X1 + (dx * 0.5);
187.131 + double dy = (this.Y1 - this.Y0) / n;
187.132 + double bottom = this.Y0 - (dy * 0.5);
187.133 + double top = this.Y1 + (dy * 0.5);
187.134 + var s00 = this.Transform(left, bottom);
187.135 + var s11 = this.Transform(right, top);
187.136 + var rect = OxyRect.Create(s00, s11);
187.137 +
187.138 + if (this.image == null || this.Data.GetHashCode() != this.dataHash)
187.139 + {
187.140 + this.UpdateImage();
187.141 + this.dataHash = this.Data.GetHashCode();
187.142 + }
187.143 +
187.144 + if (this.image != null)
187.145 + {
187.146 + var clip = this.GetClippingRect();
187.147 + rc.DrawClippedImage(clip, this.image, rect.Left, rect.Top, rect.Width, rect.Height, 1, true);
187.148 + }
187.149 + }
187.150 +
187.151 + /// <summary>
187.152 + /// Gets the point on the series that is nearest the specified point.
187.153 + /// </summary>
187.154 + /// <param name="point">
187.155 + /// The point.
187.156 + /// </param>
187.157 + /// <param name="interpolate">
187.158 + /// Interpolate the series if this flag is set to <c>true</c>.
187.159 + /// </param>
187.160 + /// <returns>
187.161 + /// A TrackerHitResult for the current hit.
187.162 + /// </returns>
187.163 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
187.164 + {
187.165 + return null;
187.166 + }
187.167 +
187.168 + /// <summary>
187.169 + /// Ensures that the axes of the series is defined.
187.170 + /// </summary>
187.171 + protected internal override void EnsureAxes()
187.172 + {
187.173 + base.EnsureAxes();
187.174 +
187.175 + this.ColorAxis =
187.176 + this.PlotModel.GetAxisOrDefault(this.ColorAxisKey, this.PlotModel.DefaultColorAxis) as ColorAxis;
187.177 + }
187.178 +
187.179 + /// <summary>
187.180 + /// Updates the max/minimum values.
187.181 + /// </summary>
187.182 + protected internal override void UpdateMaxMin()
187.183 + {
187.184 + base.UpdateMaxMin();
187.185 +
187.186 + this.MinX = Math.Min(this.X0, this.X1);
187.187 + this.MaxX = Math.Max(this.X0, this.X1);
187.188 +
187.189 + this.MinY = Math.Min(this.Y0, this.Y1);
187.190 + this.MaxY = Math.Max(this.Y0, this.Y1);
187.191 +
187.192 + this.MinValue = this.GetData().Min();
187.193 + this.MaxValue = this.GetData().Max();
187.194 +
187.195 + this.XAxis.Include(this.MinX);
187.196 + this.XAxis.Include(this.MaxX);
187.197 +
187.198 + this.YAxis.Include(this.MinY);
187.199 + this.YAxis.Include(this.MaxY);
187.200 +
187.201 + this.ColorAxis.Include(this.MinValue);
187.202 + this.ColorAxis.Include(this.MaxValue);
187.203 + }
187.204 +
187.205 + /// <summary>
187.206 + /// Gets the data as a sequence (LINQ-friendly).
187.207 + /// </summary>
187.208 + /// <returns>The sequence of data.</returns>
187.209 + protected IEnumerable<double> GetData()
187.210 + {
187.211 + int m = this.Data.GetLength(0);
187.212 + int n = this.Data.GetLength(1);
187.213 + for (int i = 0; i < m; i++)
187.214 + {
187.215 + for (int j = 0; j < n; j++)
187.216 + {
187.217 + yield return this.Data[i, j];
187.218 + }
187.219 + }
187.220 + }
187.221 +
187.222 + /// <summary>
187.223 + /// Updates the image.
187.224 + /// </summary>
187.225 + private void UpdateImage()
187.226 + {
187.227 + int m = this.Data.GetLength(0);
187.228 + int n = this.Data.GetLength(1);
187.229 + var buffer = new OxyColor[n, m];
187.230 + for (int i = 0; i < m; i++)
187.231 + {
187.232 + for (int j = 0; j < n; j++)
187.233 + {
187.234 + buffer[j, i] = this.ColorAxis.GetColor(this.Data[i, j]);
187.235 + }
187.236 + }
187.237 +
187.238 + this.image = OxyImage.PngFromArgb(buffer);
187.239 + }
187.240 + }
187.241 +}
187.242 \ No newline at end of file
188.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
188.2 +++ b/External/OxyPlot/OxyPlot/Series/HighLowItem.cs Sat Jun 08 16:53:22 2013 +0000
188.3 @@ -0,0 +1,187 @@
188.4 +// --------------------------------------------------------------------------------------------------------------------
188.5 +// <copyright file="HighLowItem.cs" company="OxyPlot">
188.6 +// The MIT License (MIT)
188.7 +//
188.8 +// Copyright (c) 2012 Oystein Bjorke
188.9 +//
188.10 +// Permission is hereby granted, free of charge, to any person obtaining a
188.11 +// copy of this software and associated documentation files (the
188.12 +// "Software"), to deal in the Software without restriction, including
188.13 +// without limitation the rights to use, copy, modify, merge, publish,
188.14 +// distribute, sublicense, and/or sell copies of the Software, and to
188.15 +// permit persons to whom the Software is furnished to do so, subject to
188.16 +// the following conditions:
188.17 +//
188.18 +// The above copyright notice and this permission notice shall be included
188.19 +// in all copies or substantial portions of the Software.
188.20 +//
188.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
188.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
188.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
188.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
188.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
188.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
188.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
188.28 +// </copyright>
188.29 +// <summary>
188.30 +// Represents an item in a HighLowSeries.
188.31 +// </summary>
188.32 +// --------------------------------------------------------------------------------------------------------------------
188.33 +namespace OxyPlot.Series
188.34 +{
188.35 + /// <summary>
188.36 + /// Represents an item in a <see cref="HighLowSeries"/>.
188.37 + /// </summary>
188.38 + public class HighLowItem
188.39 + {
188.40 + /// <summary>
188.41 + /// The undefined.
188.42 + /// </summary>
188.43 + public static readonly HighLowItem Undefined = new HighLowItem(double.NaN, double.NaN, double.NaN);
188.44 +
188.45 + /// <summary>
188.46 + /// The close.
188.47 + /// </summary>
188.48 + private double close;
188.49 +
188.50 + /// <summary>
188.51 + /// The high.
188.52 + /// </summary>
188.53 + private double high;
188.54 +
188.55 + /// <summary>
188.56 + /// The low.
188.57 + /// </summary>
188.58 + private double low;
188.59 +
188.60 + /// <summary>
188.61 + /// The open.
188.62 + /// </summary>
188.63 + private double open;
188.64 +
188.65 + /// <summary>
188.66 + /// The x.
188.67 + /// </summary>
188.68 + private double x;
188.69 +
188.70 + /// <summary>
188.71 + /// Initializes a new instance of the <see cref="HighLowItem"/> class.
188.72 + /// </summary>
188.73 + public HighLowItem()
188.74 + {
188.75 + }
188.76 +
188.77 + /// <summary>
188.78 + /// Initializes a new instance of the <see cref="HighLowItem"/> struct.
188.79 + /// </summary>
188.80 + /// <param name="x">
188.81 + /// The x value.
188.82 + /// </param>
188.83 + /// <param name="high">
188.84 + /// The high value.
188.85 + /// </param>
188.86 + /// <param name="low">
188.87 + /// The low value.
188.88 + /// </param>
188.89 + /// <param name="open">
188.90 + /// The open value.
188.91 + /// </param>
188.92 + /// <param name="close">
188.93 + /// The close value.
188.94 + /// </param>
188.95 + public HighLowItem(double x, double high, double low, double open = double.NaN, double close = double.NaN)
188.96 + {
188.97 + this.x = x;
188.98 + this.high = high;
188.99 + this.low = low;
188.100 + this.open = open;
188.101 + this.close = close;
188.102 + }
188.103 +
188.104 + /// <summary>
188.105 + /// Gets or sets the close value.
188.106 + /// </summary>
188.107 + /// <value>The close value.</value>
188.108 + public double Close
188.109 + {
188.110 + get
188.111 + {
188.112 + return this.close;
188.113 + }
188.114 +
188.115 + set
188.116 + {
188.117 + this.close = value;
188.118 + }
188.119 + }
188.120 +
188.121 + /// <summary>
188.122 + /// Gets or sets the high value.
188.123 + /// </summary>
188.124 + /// <value>The high value.</value>
188.125 + public double High
188.126 + {
188.127 + get
188.128 + {
188.129 + return this.high;
188.130 + }
188.131 +
188.132 + set
188.133 + {
188.134 + this.high = value;
188.135 + }
188.136 + }
188.137 +
188.138 + /// <summary>
188.139 + /// Gets or sets the low value.
188.140 + /// </summary>
188.141 + /// <value>The low value.</value>
188.142 + public double Low
188.143 + {
188.144 + get
188.145 + {
188.146 + return this.low;
188.147 + }
188.148 +
188.149 + set
188.150 + {
188.151 + this.low = value;
188.152 + }
188.153 + }
188.154 +
188.155 + /// <summary>
188.156 + /// Gets or sets the open value.
188.157 + /// </summary>
188.158 + /// <value>The open value.</value>
188.159 + public double Open
188.160 + {
188.161 + get
188.162 + {
188.163 + return this.open;
188.164 + }
188.165 +
188.166 + set
188.167 + {
188.168 + this.open = value;
188.169 + }
188.170 + }
188.171 +
188.172 + /// <summary>
188.173 + /// Gets or sets the X value (time).
188.174 + /// </summary>
188.175 + /// <value>The X value.</value>
188.176 + public double X
188.177 + {
188.178 + get
188.179 + {
188.180 + return this.x;
188.181 + }
188.182 +
188.183 + set
188.184 + {
188.185 + this.x = value;
188.186 + }
188.187 + }
188.188 +
188.189 + }
188.190 +}
188.191 \ No newline at end of file
189.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
189.2 +++ b/External/OxyPlot/OxyPlot/Series/HighLowSeries.cs Sat Jun 08 16:53:22 2013 +0000
189.3 @@ -0,0 +1,502 @@
189.4 +// --------------------------------------------------------------------------------------------------------------------
189.5 +// <copyright file="HighLowSeries.cs" company="OxyPlot">
189.6 +// The MIT License (MIT)
189.7 +//
189.8 +// Copyright (c) 2012 Oystein Bjorke
189.9 +//
189.10 +// Permission is hereby granted, free of charge, to any person obtaining a
189.11 +// copy of this software and associated documentation files (the
189.12 +// "Software"), to deal in the Software without restriction, including
189.13 +// without limitation the rights to use, copy, modify, merge, publish,
189.14 +// distribute, sublicense, and/or sell copies of the Software, and to
189.15 +// permit persons to whom the Software is furnished to do so, subject to
189.16 +// the following conditions:
189.17 +//
189.18 +// The above copyright notice and this permission notice shall be included
189.19 +// in all copies or substantial portions of the Software.
189.20 +//
189.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
189.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
189.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
189.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
189.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
189.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
189.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
189.28 +// </copyright>
189.29 +// <summary>
189.30 +// Represents a series for high-low plots.
189.31 +// </summary>
189.32 +// --------------------------------------------------------------------------------------------------------------------
189.33 +namespace OxyPlot.Series
189.34 +{
189.35 + using System;
189.36 + using System.Collections.Generic;
189.37 +
189.38 + using OxyPlot.Axes;
189.39 +
189.40 + /// <summary>
189.41 + /// Represents a series for high-low plots.
189.42 + /// </summary>
189.43 + /// <remarks>
189.44 + /// See http://www.mathworks.com/help/toolbox/finance/highlowfts.html
189.45 + /// </remarks>
189.46 + public class HighLowSeries : XYAxisSeries
189.47 + {
189.48 + /// <summary>
189.49 + /// High/low items
189.50 + /// </summary>
189.51 + private IList<HighLowItem> items;
189.52 +
189.53 + /// <summary>
189.54 + /// The default color.
189.55 + /// </summary>
189.56 + private OxyColor defaultColor;
189.57 +
189.58 + /// <summary>
189.59 + /// Initializes a new instance of the <see cref = "HighLowSeries" /> class.
189.60 + /// </summary>
189.61 + public HighLowSeries()
189.62 + {
189.63 + this.items = new List<HighLowItem>();
189.64 + this.TickLength = 4;
189.65 + this.StrokeThickness = 1;
189.66 + this.TrackerFormatString = "X: {1:0.00}\nHigh: {2:0.00}\nLow: {3:0.00}\nOpen: {4:0.00}\nClose: {5:0.00}";
189.67 + }
189.68 +
189.69 + /// <summary>
189.70 + /// Initializes a new instance of the <see cref="HighLowSeries"/> class.
189.71 + /// </summary>
189.72 + /// <param name="title">
189.73 + /// The title.
189.74 + /// </param>
189.75 + public HighLowSeries(string title)
189.76 + : this()
189.77 + {
189.78 + this.Title = title;
189.79 + }
189.80 +
189.81 + /// <summary>
189.82 + /// Initializes a new instance of the <see cref="HighLowSeries"/> class.
189.83 + /// </summary>
189.84 + /// <param name="color">
189.85 + /// The color.
189.86 + /// </param>
189.87 + /// <param name="strokeThickness">
189.88 + /// The stroke thickness.
189.89 + /// </param>
189.90 + /// <param name="title">
189.91 + /// The title.
189.92 + /// </param>
189.93 + public HighLowSeries(OxyColor color, double strokeThickness = 1, string title = null)
189.94 + : this()
189.95 + {
189.96 + this.Color = color;
189.97 + this.StrokeThickness = strokeThickness;
189.98 + this.Title = title;
189.99 + }
189.100 +
189.101 + /// <summary>
189.102 + /// Gets or sets the color of the curve.
189.103 + /// </summary>
189.104 + /// <value>The color.</value>
189.105 + public OxyColor Color { get; set; }
189.106 +
189.107 + /// <summary>
189.108 + /// Gets the actual color.
189.109 + /// </summary>
189.110 + /// <value>The actual color.</value>
189.111 + public OxyColor ActualColor
189.112 + {
189.113 + get { return this.Color ?? this.defaultColor; }
189.114 + }
189.115 +
189.116 + /// <summary>
189.117 + /// Gets or sets the dashes array.
189.118 + /// If this is not null it overrides the LineStyle property.
189.119 + /// </summary>
189.120 + /// <value>The dashes.</value>
189.121 + public double[] Dashes { get; set; }
189.122 +
189.123 + /// <summary>
189.124 + /// Gets or sets the data field for the Close value.
189.125 + /// </summary>
189.126 + public string DataFieldClose { get; set; }
189.127 +
189.128 + /// <summary>
189.129 + /// Gets or sets the data field for the High value.
189.130 + /// </summary>
189.131 + public string DataFieldHigh { get; set; }
189.132 +
189.133 + /// <summary>
189.134 + /// Gets or sets the data field for the Low value.
189.135 + /// </summary>
189.136 + public string DataFieldLow { get; set; }
189.137 +
189.138 + /// <summary>
189.139 + /// Gets or sets the data field for the Open value.
189.140 + /// </summary>
189.141 + public string DataFieldOpen { get; set; }
189.142 +
189.143 + /// <summary>
189.144 + /// Gets or sets the x data field (time).
189.145 + /// </summary>
189.146 + public string DataFieldX { get; set; }
189.147 +
189.148 + /// <summary>
189.149 + /// Gets or sets the points.
189.150 + /// </summary>
189.151 + /// <value>The points.</value>
189.152 + public IList<HighLowItem> Items
189.153 + {
189.154 + get
189.155 + {
189.156 + return this.items;
189.157 + }
189.158 +
189.159 + set
189.160 + {
189.161 + this.items = value;
189.162 + }
189.163 + }
189.164 +
189.165 + /// <summary>
189.166 + /// Gets or sets the line join.
189.167 + /// </summary>
189.168 + /// <value>The line join.</value>
189.169 + public OxyPenLineJoin LineJoin { get; set; }
189.170 +
189.171 + /// <summary>
189.172 + /// Gets or sets the line style.
189.173 + /// </summary>
189.174 + /// <value>The line style.</value>
189.175 + public LineStyle LineStyle { get; set; }
189.176 +
189.177 + /// <summary>
189.178 + /// Gets or sets the mapping deleagte.
189.179 + /// Example: series1.Mapping = item => new HighLowItem(((MyType)item).Time,((MyType)item).Value);
189.180 + /// </summary>
189.181 + /// <value>The mapping.</value>
189.182 + public Func<object, HighLowItem> Mapping { get; set; }
189.183 +
189.184 + /// <summary>
189.185 + /// Gets or sets the thickness of the curve.
189.186 + /// </summary>
189.187 + /// <value>The stroke thickness.</value>
189.188 + public double StrokeThickness { get; set; }
189.189 +
189.190 + /// <summary>
189.191 + /// Gets or sets the length of the open/close ticks (screen coordinates).
189.192 + /// </summary>
189.193 + /// <value>The length of the open/close ticks.</value>
189.194 + public double TickLength { get; set; }
189.195 +
189.196 + /// <summary>
189.197 + /// Gets the point on the series that is nearest the specified point.
189.198 + /// </summary>
189.199 + /// <param name="point">The point.</param>
189.200 + /// <param name="interpolate">Interpolate the series if this flag is set to <c>true</c>.</param>
189.201 + /// <returns>
189.202 + /// A TrackerHitResult for the current hit.
189.203 + /// </returns>
189.204 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
189.205 + {
189.206 + if (this.XAxis == null || this.YAxis == null)
189.207 + {
189.208 + return null;
189.209 + }
189.210 +
189.211 + if (interpolate)
189.212 + {
189.213 + return null;
189.214 + }
189.215 +
189.216 + double minimumDistance = double.MaxValue;
189.217 + var result = new TrackerHitResult(this, DataPoint.Undefined, ScreenPoint.Undefined);
189.218 +
189.219 + Action<DataPoint, HighLowItem, int> check = (p, item, index) =>
189.220 + {
189.221 + var sp = this.Transform(p);
189.222 + double dx = sp.x - point.x;
189.223 + double dy = sp.y - point.y;
189.224 + double d2 = (dx * dx) + (dy * dy);
189.225 +
189.226 + if (d2 < minimumDistance)
189.227 + {
189.228 + result.DataPoint = p;
189.229 + result.Position = sp;
189.230 + result.Item = item;
189.231 + result.Index = index;
189.232 + if (this.TrackerFormatString != null)
189.233 + {
189.234 + result.Text = StringHelper.Format(
189.235 + this.ActualCulture,
189.236 + this.TrackerFormatString,
189.237 + item,
189.238 + this.Title,
189.239 + this.XAxis.GetValue(p.X),
189.240 + item.High,
189.241 + item.Low,
189.242 + item.Open,
189.243 + item.Close);
189.244 + }
189.245 +
189.246 + minimumDistance = d2;
189.247 + }
189.248 + };
189.249 + int i = 0;
189.250 + foreach (var item in this.items)
189.251 + {
189.252 + check(new DataPoint(item.X, item.High), item, i);
189.253 + check(new DataPoint(item.X, item.Low), item, i);
189.254 + check(new DataPoint(item.X, item.Open), item, i);
189.255 + check(new DataPoint(item.X, item.Close), item, i++);
189.256 + }
189.257 +
189.258 + if (minimumDistance < double.MaxValue)
189.259 + {
189.260 + return result;
189.261 + }
189.262 +
189.263 + return null;
189.264 + }
189.265 +
189.266 + /// <summary>
189.267 + /// Determines whether the point is valid.
189.268 + /// </summary>
189.269 + /// <param name="pt">The point.</param>
189.270 + /// <param name="xaxis">The x axis.</param>
189.271 + /// <param name="yaxis">The y axis.</param>
189.272 + /// <returns>
189.273 + /// <c>true</c> if [is valid point] [the specified pt]; otherwise, <c>false</c>.
189.274 + /// </returns>
189.275 + public virtual bool IsValidItem(HighLowItem pt, Axis xaxis, Axis yaxis)
189.276 + {
189.277 + return !double.IsNaN(pt.X) && !double.IsInfinity(pt.X) && !double.IsNaN(pt.High)
189.278 + && !double.IsInfinity(pt.High) && !double.IsNaN(pt.Low) && !double.IsInfinity(pt.Low);
189.279 + }
189.280 +
189.281 + /// <summary>
189.282 + /// Renders the series on the specified rendering context.
189.283 + /// </summary>
189.284 + /// <param name="rc">
189.285 + /// The rendering context.
189.286 + /// </param>
189.287 + /// <param name="model">
189.288 + /// The owner plot model.
189.289 + /// </param>
189.290 + public override void Render(IRenderContext rc, PlotModel model)
189.291 + {
189.292 + if (this.items.Count == 0)
189.293 + {
189.294 + return;
189.295 + }
189.296 +
189.297 + this.VerifyAxes();
189.298 +
189.299 + var clippingRect = this.GetClippingRect();
189.300 +
189.301 + foreach (var v in this.items)
189.302 + {
189.303 + if (!this.IsValidItem(v, this.XAxis, this.YAxis))
189.304 + {
189.305 + continue;
189.306 + }
189.307 +
189.308 + if (this.StrokeThickness > 0 && this.LineStyle != LineStyle.None)
189.309 + {
189.310 + ScreenPoint high = this.Transform(v.X, v.High);
189.311 + ScreenPoint low = this.Transform(v.X, v.Low);
189.312 +
189.313 + rc.DrawClippedLine(
189.314 + new[] { low, high },
189.315 + clippingRect,
189.316 + 0,
189.317 + this.GetSelectableColor(this.ActualColor),
189.318 + this.StrokeThickness,
189.319 + this.LineStyle,
189.320 + this.LineJoin,
189.321 + true);
189.322 + if (!double.IsNaN(v.Open))
189.323 + {
189.324 + ScreenPoint open = this.Transform(v.X, v.Open);
189.325 + ScreenPoint openTick = open;
189.326 + openTick.X -= this.TickLength;
189.327 + rc.DrawClippedLine(
189.328 + new[] { open, openTick },
189.329 + clippingRect,
189.330 + 0,
189.331 + this.GetSelectableColor(this.ActualColor),
189.332 + this.StrokeThickness,
189.333 + this.LineStyle,
189.334 + this.LineJoin,
189.335 + true);
189.336 + }
189.337 +
189.338 + if (!double.IsNaN(v.Close))
189.339 + {
189.340 + ScreenPoint close = this.Transform(v.X, v.Close);
189.341 + ScreenPoint closeTick = close;
189.342 + closeTick.X += this.TickLength;
189.343 + rc.DrawClippedLine(
189.344 + new[] { close, closeTick },
189.345 + clippingRect,
189.346 + 0,
189.347 + this.GetSelectableColor(this.ActualColor),
189.348 + this.StrokeThickness,
189.349 + this.LineStyle,
189.350 + this.LineJoin,
189.351 + true);
189.352 + }
189.353 + }
189.354 + }
189.355 + }
189.356 +
189.357 + /// <summary>
189.358 + /// Renders the legend symbol for the series on the specified rendering context.
189.359 + /// </summary>
189.360 + /// <param name="rc">
189.361 + /// The rendering context.
189.362 + /// </param>
189.363 + /// <param name="legendBox">
189.364 + /// The bounding rectangle of the legend box.
189.365 + /// </param>
189.366 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
189.367 + {
189.368 + double xmid = (legendBox.Left + legendBox.Right) / 2;
189.369 + double yopen = legendBox.Top + ((legendBox.Bottom - legendBox.Top) * 0.7);
189.370 + double yclose = legendBox.Top + ((legendBox.Bottom - legendBox.Top) * 0.3);
189.371 + double[] dashArray = LineStyleHelper.GetDashArray(this.LineStyle);
189.372 + var color = this.GetSelectableColor(this.ActualColor);
189.373 + rc.DrawLine(
189.374 + new[] { new ScreenPoint(xmid, legendBox.Top), new ScreenPoint(xmid, legendBox.Bottom) },
189.375 + color,
189.376 + this.StrokeThickness,
189.377 + dashArray,
189.378 + OxyPenLineJoin.Miter,
189.379 + true);
189.380 + rc.DrawLine(
189.381 + new[] { new ScreenPoint(xmid - this.TickLength, yopen), new ScreenPoint(xmid, yopen) },
189.382 + color,
189.383 + this.StrokeThickness,
189.384 + dashArray,
189.385 + OxyPenLineJoin.Miter,
189.386 + true);
189.387 + rc.DrawLine(
189.388 + new[] { new ScreenPoint(xmid + this.TickLength, yclose), new ScreenPoint(xmid, yclose) },
189.389 + color,
189.390 + this.StrokeThickness,
189.391 + dashArray,
189.392 + OxyPenLineJoin.Miter,
189.393 + true);
189.394 + }
189.395 +
189.396 + /// <summary>
189.397 + /// Sets the default values.
189.398 + /// </summary>
189.399 + /// <param name="model">
189.400 + /// The model.
189.401 + /// </param>
189.402 + protected internal override void SetDefaultValues(PlotModel model)
189.403 + {
189.404 + if (this.Color == null)
189.405 + {
189.406 + this.LineStyle = model.GetDefaultLineStyle();
189.407 + this.defaultColor = model.GetDefaultColor();
189.408 + }
189.409 + }
189.410 +
189.411 + /// <summary>
189.412 + /// Updates the data.
189.413 + /// </summary>
189.414 + protected internal override void UpdateData()
189.415 + {
189.416 + if (this.ItemsSource == null)
189.417 + {
189.418 + return;
189.419 + }
189.420 +
189.421 + this.items.Clear();
189.422 +
189.423 + // Use the mapping to generate the points
189.424 + if (this.Mapping != null)
189.425 + {
189.426 + foreach (var item in this.ItemsSource)
189.427 + {
189.428 + this.items.Add(this.Mapping(item));
189.429 + }
189.430 +
189.431 + return;
189.432 + }
189.433 +
189.434 + var filler = new ListFiller<HighLowItem>();
189.435 + filler.Add(this.DataFieldX, (p, v) => p.X = this.ToDouble(v));
189.436 + filler.Add(this.DataFieldHigh, (p, v) => p.High = this.ToDouble(v));
189.437 + filler.Add(this.DataFieldLow, (p, v) => p.Low = this.ToDouble(v));
189.438 + filler.Add(this.DataFieldOpen, (p, v) => p.Open = this.ToDouble(v));
189.439 + filler.Add(this.DataFieldClose, (p, v) => p.Close = this.ToDouble(v));
189.440 + filler.FillT(this.items, this.ItemsSource);
189.441 + }
189.442 +
189.443 + /// <summary>
189.444 + /// Updates the max/min values.
189.445 + /// </summary>
189.446 + protected internal override void UpdateMaxMin()
189.447 + {
189.448 + base.UpdateMaxMin();
189.449 + this.InternalUpdateMaxMin(this.items);
189.450 + }
189.451 +
189.452 + /// <summary>
189.453 + /// Updates the Max/Min limits from the specified point list.
189.454 + /// </summary>
189.455 + /// <param name="pts">
189.456 + /// The PTS.
189.457 + /// </param>
189.458 + protected void InternalUpdateMaxMin(IList<HighLowItem> pts)
189.459 + {
189.460 + if (pts == null || pts.Count == 0)
189.461 + {
189.462 + return;
189.463 + }
189.464 +
189.465 + double minx = this.MinX;
189.466 + double miny = this.MinY;
189.467 + double maxx = this.MaxX;
189.468 + double maxy = this.MaxY;
189.469 +
189.470 + foreach (var pt in pts)
189.471 + {
189.472 + if (!this.IsValidItem(pt, this.XAxis, this.YAxis))
189.473 + {
189.474 + continue;
189.475 + }
189.476 +
189.477 + if (pt.X < minx || double.IsNaN(minx))
189.478 + {
189.479 + minx = pt.X;
189.480 + }
189.481 +
189.482 + if (pt.X > maxx || double.IsNaN(maxx))
189.483 + {
189.484 + maxx = pt.X;
189.485 + }
189.486 +
189.487 + if (pt.Low < miny || double.IsNaN(miny))
189.488 + {
189.489 + miny = pt.Low;
189.490 + }
189.491 +
189.492 + if (pt.High > maxy || double.IsNaN(maxy))
189.493 + {
189.494 + maxy = pt.High;
189.495 + }
189.496 + }
189.497 +
189.498 + this.MinX = minx;
189.499 + this.MinY = miny;
189.500 + this.MaxX = maxx;
189.501 + this.MaxY = maxy;
189.502 + }
189.503 +
189.504 + }
189.505 +}
189.506 \ No newline at end of file
190.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
190.2 +++ b/External/OxyPlot/OxyPlot/Series/ITrackableSeries.cs Sat Jun 08 16:53:22 2013 +0000
190.3 @@ -0,0 +1,67 @@
190.4 +// --------------------------------------------------------------------------------------------------------------------
190.5 +// <copyright file="ITrackableSeries.cs" company="OxyPlot">
190.6 +// The MIT License (MIT)
190.7 +//
190.8 +// Copyright (c) 2012 Oystein Bjorke
190.9 +//
190.10 +// Permission is hereby granted, free of charge, to any person obtaining a
190.11 +// copy of this software and associated documentation files (the
190.12 +// "Software"), to deal in the Software without restriction, including
190.13 +// without limitation the rights to use, copy, modify, merge, publish,
190.14 +// distribute, sublicense, and/or sell copies of the Software, and to
190.15 +// permit persons to whom the Software is furnished to do so, subject to
190.16 +// the following conditions:
190.17 +//
190.18 +// The above copyright notice and this permission notice shall be included
190.19 +// in all copies or substantial portions of the Software.
190.20 +//
190.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
190.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
190.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
190.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
190.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
190.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
190.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
190.28 +// </copyright>
190.29 +// <summary>
190.30 +// Interface for Series that can be 'tracked'
190.31 +// </summary>
190.32 +// --------------------------------------------------------------------------------------------------------------------
190.33 +namespace OxyPlot.Series
190.34 +{
190.35 + /// <summary>
190.36 + /// Provides functionality to return data for a tracker control.
190.37 + /// </summary>
190.38 + /// <remarks>
190.39 + /// The plot control will show a tracker with the current value when moving the mouse over the data.
190.40 + /// </remarks>
190.41 + public interface ITrackableSeries
190.42 + {
190.43 + /// <summary>
190.44 + /// Gets a format string used for the tracker.
190.45 + /// </summary>
190.46 + /// <remarks>
190.47 + /// The fields that can be used in the format string depends on the series.
190.48 + /// </remarks>
190.49 + string TrackerFormatString { get; }
190.50 +
190.51 + /// <summary>
190.52 + /// Gets the tracker key.
190.53 + /// </summary>
190.54 + string TrackerKey { get; }
190.55 +
190.56 + /// <summary>
190.57 + /// Gets the point on the series that is nearest the specified point.
190.58 + /// </summary>
190.59 + /// <param name="point">
190.60 + /// The point.
190.61 + /// </param>
190.62 + /// <param name="interpolate">
190.63 + /// Interpolate the series if this flag is set to <c>true</c>.
190.64 + /// </param>
190.65 + /// <returns>
190.66 + /// A TrackerHitResult for the current hit.
190.67 + /// </returns>
190.68 + TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate);
190.69 + }
190.70 +}
190.71 \ No newline at end of file
191.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
191.2 +++ b/External/OxyPlot/OxyPlot/Series/ItemsSeries.cs Sat Jun 08 16:53:22 2013 +0000
191.3 @@ -0,0 +1,96 @@
191.4 +// --------------------------------------------------------------------------------------------------------------------
191.5 +// <copyright file="ItemsSeries.cs" company="OxyPlot">
191.6 +// The MIT License (MIT)
191.7 +//
191.8 +// Copyright (c) 2012 Oystein Bjorke
191.9 +//
191.10 +// Permission is hereby granted, free of charge, to any person obtaining a
191.11 +// copy of this software and associated documentation files (the
191.12 +// "Software"), to deal in the Software without restriction, including
191.13 +// without limitation the rights to use, copy, modify, merge, publish,
191.14 +// distribute, sublicense, and/or sell copies of the Software, and to
191.15 +// permit persons to whom the Software is furnished to do so, subject to
191.16 +// the following conditions:
191.17 +//
191.18 +// The above copyright notice and this permission notice shall be included
191.19 +// in all copies or substantial portions of the Software.
191.20 +//
191.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
191.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
191.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
191.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
191.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
191.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
191.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
191.28 +// </copyright>
191.29 +// <summary>
191.30 +// Abstract base class for series that can contain items.
191.31 +// </summary>
191.32 +// --------------------------------------------------------------------------------------------------------------------
191.33 +namespace OxyPlot.Series
191.34 +{
191.35 + using System.Collections;
191.36 + using System.Linq;
191.37 +
191.38 + /// <summary>
191.39 + /// Abstract base class for series that can contain items.
191.40 + /// </summary>
191.41 + public abstract class ItemsSeries : Series
191.42 + {
191.43 + /// <summary>
191.44 + /// Gets or sets the items source.
191.45 + /// </summary>
191.46 + /// <value> The items source. </value>
191.47 + [CodeGeneration(false)]
191.48 + public IEnumerable ItemsSource { get; set; }
191.49 +
191.50 + /// <summary>
191.51 + /// Updates the valid items
191.52 + /// </summary>
191.53 + protected internal override void UpdateValidData()
191.54 + {
191.55 + }
191.56 +
191.57 + /// <summary>
191.58 + /// Gets the item for the specified index.
191.59 + /// </summary>
191.60 + /// <param name="itemsSource"> The items source. </param>
191.61 + /// <param name="index"> The index. </param>
191.62 + /// <returns> The get item. </returns>
191.63 + /// <remarks>
191.64 + /// Returns null if ItemsSource is not set, or the index is outside the boundaries.
191.65 + /// </remarks>
191.66 + protected static object GetItem(IEnumerable itemsSource, int index)
191.67 + {
191.68 + if (itemsSource == null || index < 0)
191.69 + {
191.70 + return null;
191.71 + }
191.72 +
191.73 + var list = itemsSource as IList;
191.74 + if (list != null)
191.75 + {
191.76 + if (index < list.Count && index >= 0)
191.77 + {
191.78 + return list[index];
191.79 + }
191.80 +
191.81 + return null;
191.82 + }
191.83 +
191.84 + var i = 0;
191.85 + return itemsSource.Cast<object>().FirstOrDefault(item => i++ == index);
191.86 + }
191.87 +
191.88 + /// <summary>
191.89 + /// Gets the item at the specified index.
191.90 + /// </summary>
191.91 + /// <param name="i"> The index of the item. </param>
191.92 + /// <returns> The item of the index. </returns>
191.93 + protected virtual object GetItem(int i)
191.94 + {
191.95 + return GetItem(this.ItemsSource, i);
191.96 + }
191.97 +
191.98 + }
191.99 +}
191.100 \ No newline at end of file
192.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
192.2 +++ b/External/OxyPlot/OxyPlot/Series/LineLegendPosition.cs Sat Jun 08 16:53:22 2013 +0000
192.3 @@ -0,0 +1,52 @@
192.4 +// --------------------------------------------------------------------------------------------------------------------
192.5 +// <copyright file="LineLegendPosition.cs" company="OxyPlot">
192.6 +// The MIT License (MIT)
192.7 +//
192.8 +// Copyright (c) 2012 Oystein Bjorke
192.9 +//
192.10 +// Permission is hereby granted, free of charge, to any person obtaining a
192.11 +// copy of this software and associated documentation files (the
192.12 +// "Software"), to deal in the Software without restriction, including
192.13 +// without limitation the rights to use, copy, modify, merge, publish,
192.14 +// distribute, sublicense, and/or sell copies of the Software, and to
192.15 +// permit persons to whom the Software is furnished to do so, subject to
192.16 +// the following conditions:
192.17 +//
192.18 +// The above copyright notice and this permission notice shall be included
192.19 +// in all copies or substantial portions of the Software.
192.20 +//
192.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
192.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
192.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
192.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
192.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
192.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
192.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
192.28 +// </copyright>
192.29 +// <summary>
192.30 +// Specifies the position of legends rendered on a line series.
192.31 +// </summary>
192.32 +// --------------------------------------------------------------------------------------------------------------------
192.33 +namespace OxyPlot.Series
192.34 +{
192.35 + /// <summary>
192.36 + /// Specifies the position of legends rendered on a <see cref="LineSeries"/>.
192.37 + /// </summary>
192.38 + public enum LineLegendPosition
192.39 + {
192.40 + /// <summary>
192.41 + /// Do not render legend on the line.
192.42 + /// </summary>
192.43 + None,
192.44 +
192.45 + /// <summary>
192.46 + /// Render legend at the start of the line.
192.47 + /// </summary>
192.48 + Start,
192.49 +
192.50 + /// <summary>
192.51 + /// Render legend at the end of the line.
192.52 + /// </summary>
192.53 + End
192.54 + }
192.55 +}
192.56 \ No newline at end of file
193.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
193.2 +++ b/External/OxyPlot/OxyPlot/Series/LineSeries.cs Sat Jun 08 16:53:22 2013 +0000
193.3 @@ -0,0 +1,644 @@
193.4 +// --------------------------------------------------------------------------------------------------------------------
193.5 +// <copyright file="LineSeries.cs" company="OxyPlot">
193.6 +// The MIT License (MIT)
193.7 +//
193.8 +// Copyright (c) 2012 Oystein Bjorke
193.9 +//
193.10 +// Permission is hereby granted, free of charge, to any person obtaining a
193.11 +// copy of this software and associated documentation files (the
193.12 +// "Software"), to deal in the Software without restriction, including
193.13 +// without limitation the rights to use, copy, modify, merge, publish,
193.14 +// distribute, sublicense, and/or sell copies of the Software, and to
193.15 +// permit persons to whom the Software is furnished to do so, subject to
193.16 +// the following conditions:
193.17 +//
193.18 +// The above copyright notice and this permission notice shall be included
193.19 +// in all copies or substantial portions of the Software.
193.20 +//
193.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
193.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
193.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
193.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
193.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
193.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
193.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
193.28 +// </copyright>
193.29 +// <summary>
193.30 +// Represents a line series.
193.31 +// </summary>
193.32 +// --------------------------------------------------------------------------------------------------------------------
193.33 +
193.34 +namespace OxyPlot.Series
193.35 +{
193.36 + using System;
193.37 + using System.Collections.Generic;
193.38 +
193.39 + /// <summary>
193.40 + /// Represents a line series.
193.41 + /// </summary>
193.42 + public class LineSeries : DataPointSeries
193.43 + {
193.44 + /// <summary>
193.45 + /// The divisor value used to calculate tolerance for line smoothing.
193.46 + /// </summary>
193.47 + private const double ToleranceDivisor = 200;
193.48 +
193.49 + /// <summary>
193.50 + /// The default color.
193.51 + /// </summary>
193.52 + private OxyColor defaultColor;
193.53 +
193.54 + /// <summary>
193.55 + /// The smoothed points.
193.56 + /// </summary>
193.57 + private IList<IDataPoint> smoothedPoints;
193.58 +
193.59 + /// <summary>
193.60 + /// Initializes a new instance of the <see cref = "LineSeries" /> class.
193.61 + /// </summary>
193.62 + public LineSeries()
193.63 + {
193.64 + this.MinimumSegmentLength = 2;
193.65 + this.StrokeThickness = 2;
193.66 + this.LineJoin = OxyPenLineJoin.Bevel;
193.67 + this.LineStyle = LineStyle.Undefined;
193.68 + this.MarkerSize = 3;
193.69 + this.MarkerStrokeThickness = 1;
193.70 + this.CanTrackerInterpolatePoints = true;
193.71 + this.LabelMargin = 6;
193.72 + }
193.73 +
193.74 + /// <summary>
193.75 + /// Initializes a new instance of the <see cref="LineSeries"/> class.
193.76 + /// </summary>
193.77 + /// <param name="title">
193.78 + /// The title.
193.79 + /// </param>
193.80 + public LineSeries(string title)
193.81 + : this()
193.82 + {
193.83 + this.Title = title;
193.84 + }
193.85 +
193.86 + /// <summary>
193.87 + /// Initializes a new instance of the <see cref="LineSeries"/> class.
193.88 + /// </summary>
193.89 + /// <param name="color">
193.90 + /// The color of the line stroke.
193.91 + /// </param>
193.92 + /// <param name="strokeThickness">
193.93 + /// The stroke thickness (optional).
193.94 + /// </param>
193.95 + /// <param name="title">
193.96 + /// The title (optional).
193.97 + /// </param>
193.98 + public LineSeries(OxyColor color, double strokeThickness = 1, string title = null)
193.99 + : this()
193.100 + {
193.101 + this.Color = color;
193.102 + this.StrokeThickness = strokeThickness;
193.103 + this.BrokenLineThickness = 0;
193.104 + this.Title = title;
193.105 + }
193.106 +
193.107 + /// <summary>
193.108 + /// Gets or sets the color of the curve.
193.109 + /// </summary>
193.110 + /// <value>The color.</value>
193.111 + public OxyColor Color { get; set; }
193.112 +
193.113 + /// <summary>
193.114 + /// Gets or sets the color of the broken line segments.
193.115 + /// </summary>
193.116 + /// <remarks>
193.117 + /// Add <c>DataPoint.Undefined</c> in the Points collection to create breaks in the line.
193.118 + /// </remarks>
193.119 + public OxyColor BrokenLineColor { get; set; }
193.120 +
193.121 + /// <summary>
193.122 + /// Gets or sets the broken line style.
193.123 + /// </summary>
193.124 + public LineStyle BrokenLineStyle { get; set; }
193.125 +
193.126 + /// <summary>
193.127 + /// Gets or sets the broken line thickness.
193.128 + /// </summary>
193.129 + public double BrokenLineThickness { get; set; }
193.130 +
193.131 + /// <summary>
193.132 + /// Gets or sets the dashes array.
193.133 + /// If this is not null it overrides the LineStyle property.
193.134 + /// </summary>
193.135 + /// <value>The dashes.</value>
193.136 + public double[] Dashes { get; set; }
193.137 +
193.138 + /// <summary>
193.139 + /// Gets or sets the label format string.
193.140 + /// </summary>
193.141 + /// <value> The label format string. </value>
193.142 + public string LabelFormatString { get; set; }
193.143 +
193.144 + /// <summary>
193.145 + /// Gets or sets the label margins.
193.146 + /// </summary>
193.147 + public double LabelMargin { get; set; }
193.148 +
193.149 + /// <summary>
193.150 + /// Gets or sets the line join.
193.151 + /// </summary>
193.152 + /// <value>The line join.</value>
193.153 + public OxyPenLineJoin LineJoin { get; set; }
193.154 +
193.155 + /// <summary>
193.156 + /// Gets or sets the line style.
193.157 + /// </summary>
193.158 + /// <value>The line style.</value>
193.159 + public LineStyle LineStyle { get; set; }
193.160 +
193.161 + /// <summary>
193.162 + /// Gets or sets a value specifying the position of a legend rendered on the line.
193.163 + /// </summary>
193.164 + /// <value>A value specifying the position of the legend.</value>
193.165 + public LineLegendPosition LineLegendPosition { get; set; }
193.166 +
193.167 + /// <summary>
193.168 + /// Gets or sets the marker fill color.
193.169 + /// </summary>
193.170 + /// <value>The marker fill.</value>
193.171 + public OxyColor MarkerFill { get; set; }
193.172 +
193.173 + /// <summary>
193.174 + /// Gets or sets the marker outline polygon.
193.175 + /// If this property is set, the MarkerType will not be used.
193.176 + /// </summary>
193.177 + /// <value>The marker outline.</value>
193.178 + public ScreenPoint[] MarkerOutline { get; set; }
193.179 +
193.180 + /// <summary>
193.181 + /// Gets or sets the size of the marker.
193.182 + /// </summary>
193.183 + /// <value>The size of the marker.</value>
193.184 + public double MarkerSize { get; set; }
193.185 +
193.186 + /// <summary>
193.187 + /// Gets or sets the marker stroke.
193.188 + /// </summary>
193.189 + /// <value>The marker stroke.</value>
193.190 + public OxyColor MarkerStroke { get; set; }
193.191 +
193.192 + /// <summary>
193.193 + /// Gets or sets the marker stroke thickness.
193.194 + /// </summary>
193.195 + /// <value>The marker stroke thickness.</value>
193.196 + public double MarkerStrokeThickness { get; set; }
193.197 +
193.198 + /// <summary>
193.199 + /// Gets or sets the type of the marker.
193.200 + /// </summary>
193.201 + /// <value>The type of the marker.</value>
193.202 + /// <remarks>
193.203 + /// If MarkerType.Custom is used, the MarkerOutline property must be specified.
193.204 + /// </remarks>
193.205 + public MarkerType MarkerType { get; set; }
193.206 +
193.207 + /// <summary>
193.208 + /// Gets or sets the minimum length of the segment.
193.209 + /// Increasing this number will increase performance,
193.210 + /// but make the curve less accurate.
193.211 + /// </summary>
193.212 + /// <value>The minimum length of the segment.</value>
193.213 + public double MinimumSegmentLength { get; set; }
193.214 +
193.215 + /// <summary>
193.216 + /// Gets or sets the thickness of the curve.
193.217 + /// </summary>
193.218 + /// <value>The stroke thickness.</value>
193.219 + public double StrokeThickness { get; set; }
193.220 +
193.221 + /// <summary>
193.222 + /// Gets the actual color.
193.223 + /// </summary>
193.224 + /// <value>The actual color.</value>
193.225 + protected OxyColor ActualColor
193.226 + {
193.227 + get
193.228 + {
193.229 + return this.Color ?? this.defaultColor;
193.230 + }
193.231 + }
193.232 +
193.233 + /// <summary>
193.234 + /// Gets the actual line style.
193.235 + /// </summary>
193.236 + /// <value>
193.237 + /// The actual line style.
193.238 + /// </value>
193.239 + protected LineStyle ActualLineStyle
193.240 + {
193.241 + get
193.242 + {
193.243 + return this.LineStyle != LineStyle.Undefined ? this.LineStyle : LineStyle.Solid;
193.244 + }
193.245 + }
193.246 +
193.247 + /// <summary>
193.248 + /// Gets the smoothed points.
193.249 + /// </summary>
193.250 + /// <value>The smoothed points.</value>
193.251 + protected IList<IDataPoint> SmoothedPoints
193.252 + {
193.253 + get
193.254 + {
193.255 + return this.smoothedPoints;
193.256 + }
193.257 + }
193.258 +
193.259 + /// <summary>
193.260 + /// Gets the point on the series that is nearest the specified point.
193.261 + /// </summary>
193.262 + /// <param name="point">The point.</param>
193.263 + /// <param name="interpolate">Interpolate the series if this flag is set to <c>true</c>.</param>
193.264 + /// <returns>
193.265 + /// A TrackerHitResult for the current hit.
193.266 + /// </returns>
193.267 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
193.268 + {
193.269 + if (interpolate)
193.270 + {
193.271 + // Cannot interpolate if there is no line
193.272 + if (this.ActualColor == null || this.StrokeThickness.IsZero())
193.273 + {
193.274 + return null;
193.275 + }
193.276 +
193.277 + if (!this.CanTrackerInterpolatePoints)
193.278 + {
193.279 + return null;
193.280 + }
193.281 + }
193.282 +
193.283 + if (interpolate && this.Smooth && this.SmoothedPoints != null)
193.284 + {
193.285 + return this.GetNearestInterpolatedPointInternal(this.SmoothedPoints, point);
193.286 + }
193.287 +
193.288 + return base.GetNearestPoint(point, interpolate);
193.289 + }
193.290 +
193.291 + /// <summary>
193.292 + /// Renders the series on the specified rendering context.
193.293 + /// </summary>
193.294 + /// <param name="rc">
193.295 + /// The rendering context.
193.296 + /// </param>
193.297 + /// <param name="model">
193.298 + /// The owner plot model.
193.299 + /// </param>
193.300 + public override void Render(IRenderContext rc, PlotModel model)
193.301 + {
193.302 + if (this.Points.Count == 0)
193.303 + {
193.304 + return;
193.305 + }
193.306 +
193.307 + this.VerifyAxes();
193.308 +
193.309 + var clippingRect = this.GetClippingRect();
193.310 + var transformedPoints = new List<ScreenPoint>();
193.311 + var lineBreakSegments = new List<ScreenPoint>();
193.312 +
193.313 + ScreenPoint lastValidPoint = default(ScreenPoint);
193.314 + bool isBroken = false;
193.315 + var renderBrokenLineSegments = this.BrokenLineThickness > 0 && this.BrokenLineStyle != LineStyle.None;
193.316 +
193.317 + // Transform all points to screen coordinates
193.318 + // Render the line when invalid points occur
193.319 + foreach (var point in this.Points)
193.320 + {
193.321 + if (!this.IsValidPoint(point, this.XAxis, this.YAxis))
193.322 + {
193.323 + this.RenderPoints(rc, clippingRect, transformedPoints);
193.324 + transformedPoints.Clear();
193.325 + isBroken = true;
193.326 + continue;
193.327 + }
193.328 +
193.329 + var pt = this.XAxis.Transform(point.X, point.Y, this.YAxis);
193.330 + transformedPoints.Add(pt);
193.331 +
193.332 + if (renderBrokenLineSegments)
193.333 + {
193.334 + if (isBroken)
193.335 + {
193.336 + lineBreakSegments.Add(lastValidPoint);
193.337 + lineBreakSegments.Add(pt);
193.338 + isBroken = false;
193.339 + }
193.340 +
193.341 + lastValidPoint = pt;
193.342 + }
193.343 + }
193.344 +
193.345 + // Render the remaining points
193.346 + this.RenderPoints(rc, clippingRect, transformedPoints);
193.347 +
193.348 + if (renderBrokenLineSegments)
193.349 + {
193.350 + // Render line breaks
193.351 + rc.DrawClippedLineSegments(
193.352 + lineBreakSegments,
193.353 + clippingRect,
193.354 + this.BrokenLineColor,
193.355 + this.BrokenLineThickness,
193.356 + this.BrokenLineStyle,
193.357 + this.LineJoin,
193.358 + false);
193.359 + }
193.360 +
193.361 + if (this.LabelFormatString != null)
193.362 + {
193.363 + // render point labels (not optimized for performance)
193.364 + this.RenderPointLabels(rc, clippingRect);
193.365 + }
193.366 +
193.367 + if (this.LineLegendPosition != LineLegendPosition.None && this.Points.Count > 0
193.368 + && !string.IsNullOrEmpty(this.Title))
193.369 + {
193.370 + // renders a legend on the line
193.371 + this.RenderLegendOnLine(rc, clippingRect);
193.372 + }
193.373 + }
193.374 +
193.375 + /// <summary>
193.376 + /// Renders the legend symbol for the line series on the
193.377 + /// specified rendering context.
193.378 + /// </summary>
193.379 + /// <param name="rc">
193.380 + /// The rendering context.
193.381 + /// </param>
193.382 + /// <param name="legendBox">
193.383 + /// The bounding rectangle of the legend box.
193.384 + /// </param>
193.385 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
193.386 + {
193.387 + double xmid = (legendBox.Left + legendBox.Right) / 2;
193.388 + double ymid = (legendBox.Top + legendBox.Bottom) / 2;
193.389 + var pts = new[] { new ScreenPoint(legendBox.Left, ymid), new ScreenPoint(legendBox.Right, ymid) };
193.390 + rc.DrawLine(
193.391 + pts,
193.392 + this.GetSelectableColor(this.ActualColor),
193.393 + this.StrokeThickness,
193.394 + this.ActualLineStyle.GetDashArray());
193.395 + var midpt = new ScreenPoint(xmid, ymid);
193.396 + rc.DrawMarker(
193.397 + midpt,
193.398 + legendBox,
193.399 + this.MarkerType,
193.400 + this.MarkerOutline,
193.401 + this.MarkerSize,
193.402 + this.MarkerFill,
193.403 + this.MarkerStroke,
193.404 + this.MarkerStrokeThickness);
193.405 + }
193.406 +
193.407 + /// <summary>
193.408 + /// The set default values.
193.409 + /// </summary>
193.410 + /// <param name="model">
193.411 + /// The model.
193.412 + /// </param>
193.413 + protected internal override void SetDefaultValues(PlotModel model)
193.414 + {
193.415 + // todo: should use ActualLineStyle
193.416 + if (this.Color == null)
193.417 + {
193.418 + if (this.LineStyle == LineStyle.Undefined)
193.419 + {
193.420 + this.LineStyle = model.GetDefaultLineStyle();
193.421 + }
193.422 +
193.423 + this.defaultColor = model.GetDefaultColor();
193.424 +
193.425 + // And MarkerFill will be overridden if not set to null
193.426 + if (this.MarkerFill == null)
193.427 + {
193.428 + this.MarkerFill = this.defaultColor;
193.429 + }
193.430 + }
193.431 + }
193.432 +
193.433 + /// <summary>
193.434 + /// Updates the axes to include the max and min of this series.
193.435 + /// </summary>
193.436 + protected internal override void UpdateMaxMin()
193.437 + {
193.438 + if (this.Smooth)
193.439 + {
193.440 + // Update the max/min from the control points
193.441 + base.UpdateMaxMin();
193.442 +
193.443 + // Make sure the smooth points are re-evaluated.
193.444 + this.ResetSmoothedPoints();
193.445 +
193.446 + // Update the max/min from the smoothed points
193.447 + foreach (var pt in this.SmoothedPoints)
193.448 + {
193.449 + this.MinX = Math.Min(this.MinX, pt.X);
193.450 + this.MinY = Math.Min(this.MinY, pt.Y);
193.451 + this.MaxX = Math.Max(this.MaxX, pt.X);
193.452 + this.MaxY = Math.Max(this.MaxY, pt.Y);
193.453 + }
193.454 + }
193.455 + else
193.456 + {
193.457 + base.UpdateMaxMin();
193.458 + }
193.459 + }
193.460 +
193.461 + /// <summary>
193.462 + /// Renders the point labels.
193.463 + /// </summary>
193.464 + /// <param name="rc">The render context.</param>
193.465 + /// <param name="clippingRect">The clipping rectangle.</param>
193.466 + protected void RenderPointLabels(IRenderContext rc, OxyRect clippingRect)
193.467 + {
193.468 + int index = -1;
193.469 + foreach (var point in this.Points)
193.470 + {
193.471 + index++;
193.472 +
193.473 + if (!this.IsValidPoint(point, this.XAxis, this.YAxis))
193.474 + {
193.475 + continue;
193.476 + }
193.477 +
193.478 + var pt = this.XAxis.Transform(point.X, point.Y, this.YAxis);
193.479 + pt.Y -= this.LabelMargin;
193.480 +
193.481 + if (!clippingRect.Contains(pt))
193.482 + {
193.483 + continue;
193.484 + }
193.485 +
193.486 + var s = StringHelper.Format(
193.487 + this.ActualCulture, this.LabelFormatString, this.GetItem(index), point.X, point.Y);
193.488 +
193.489 +#if SUPPORTLABELPLACEMENT
193.490 + switch (this.LabelPlacement)
193.491 + {
193.492 + case LabelPlacement.Inside:
193.493 + pt = new ScreenPoint(rect.Right - this.LabelMargin, (rect.Top + rect.Bottom) / 2);
193.494 + ha = HorizontalAlignment.Right;
193.495 + break;
193.496 + case LabelPlacement.Middle:
193.497 + pt = new ScreenPoint((rect.Left + rect.Right) / 2, (rect.Top + rect.Bottom) / 2);
193.498 + ha = HorizontalAlignment.Center;
193.499 + break;
193.500 + case LabelPlacement.Base:
193.501 + pt = new ScreenPoint(rect.Left + this.LabelMargin, (rect.Top + rect.Bottom) / 2);
193.502 + ha = HorizontalAlignment.Left;
193.503 + break;
193.504 + default: // Outside
193.505 + pt = new ScreenPoint(rect.Right + this.LabelMargin, (rect.Top + rect.Bottom) / 2);
193.506 + ha = HorizontalAlignment.Left;
193.507 + break;
193.508 + }
193.509 +#endif
193.510 +
193.511 + rc.DrawClippedText(
193.512 + clippingRect,
193.513 + pt,
193.514 + s,
193.515 + this.ActualTextColor,
193.516 + this.ActualFont,
193.517 + this.ActualFontSize,
193.518 + this.ActualFontWeight,
193.519 + 0,
193.520 + HorizontalAlignment.Center,
193.521 + VerticalAlignment.Bottom);
193.522 + }
193.523 + }
193.524 +
193.525 + /// <summary>
193.526 + /// Renders a legend on the line.
193.527 + /// </summary>
193.528 + /// <param name="rc">The render context.</param>
193.529 + /// <param name="clippingRect">The clipping rectangle.</param>
193.530 + protected void RenderLegendOnLine(IRenderContext rc, OxyRect clippingRect)
193.531 + {
193.532 + // Find the position
193.533 + IDataPoint point;
193.534 + var ha = HorizontalAlignment.Left;
193.535 + double dx;
193.536 + switch (this.LineLegendPosition)
193.537 + {
193.538 + case LineLegendPosition.Start:
193.539 +
193.540 + // start position
193.541 + point = this.Points[0];
193.542 + ha = HorizontalAlignment.Right;
193.543 + dx = -4;
193.544 + break;
193.545 + default:
193.546 +
193.547 + // end position
193.548 + point = this.Points[this.Points.Count - 1];
193.549 + dx = 4;
193.550 + break;
193.551 + }
193.552 +
193.553 + var pt = this.XAxis.Transform(point.X, point.Y, this.YAxis);
193.554 + pt.X += dx;
193.555 +
193.556 + // Render the legend
193.557 + rc.DrawClippedText(
193.558 + clippingRect,
193.559 + pt,
193.560 + this.Title,
193.561 + this.ActualTextColor,
193.562 + this.ActualFont,
193.563 + this.ActualFontSize,
193.564 + this.ActualFontWeight,
193.565 + 0,
193.566 + ha,
193.567 + VerticalAlignment.Middle);
193.568 + }
193.569 +
193.570 + /// <summary>
193.571 + /// Renders the transformed points.
193.572 + /// </summary>
193.573 + /// <param name="rc">
193.574 + /// The render context.
193.575 + /// </param>
193.576 + /// <param name="clippingRect">
193.577 + /// The clipping rectangle.
193.578 + /// </param>
193.579 + /// <param name="pointsToRender">
193.580 + /// The points to render.
193.581 + /// </param>
193.582 + protected void RenderPoints(IRenderContext rc, OxyRect clippingRect, IList<ScreenPoint> pointsToRender)
193.583 + {
193.584 + var screenPoints = pointsToRender;
193.585 + if (this.Smooth)
193.586 + {
193.587 + // spline smoothing (should only be used on small datasets)
193.588 + var resampledPoints = ScreenPointHelper.ResamplePoints(pointsToRender, this.MinimumSegmentLength);
193.589 + screenPoints = CanonicalSplineHelper.CreateSpline(resampledPoints, 0.5, null, false, 0.25);
193.590 + }
193.591 +
193.592 + // clip the line segments with the clipping rectangle
193.593 + if (this.StrokeThickness > 0 && this.ActualLineStyle != LineStyle.None)
193.594 + {
193.595 + this.RenderSmoothedLine(rc, clippingRect, screenPoints);
193.596 + }
193.597 +
193.598 + if (this.MarkerType != MarkerType.None)
193.599 + {
193.600 + rc.DrawMarkers(
193.601 + pointsToRender,
193.602 + clippingRect,
193.603 + this.MarkerType,
193.604 + this.MarkerOutline,
193.605 + new[] { this.MarkerSize },
193.606 + this.MarkerFill,
193.607 + this.MarkerStroke,
193.608 + this.MarkerStrokeThickness);
193.609 + }
193.610 + }
193.611 +
193.612 + /// <summary>
193.613 + /// Renders the (smoothed) line.
193.614 + /// </summary>
193.615 + /// <param name="rc">
193.616 + /// The render context.
193.617 + /// </param>
193.618 + /// <param name="clippingRect">
193.619 + /// The clipping rectangle.
193.620 + /// </param>
193.621 + /// <param name="pointsToRender">
193.622 + /// The points to render.
193.623 + /// </param>
193.624 + protected virtual void RenderSmoothedLine(
193.625 + IRenderContext rc, OxyRect clippingRect, IList<ScreenPoint> pointsToRender)
193.626 + {
193.627 + rc.DrawClippedLine(
193.628 + pointsToRender,
193.629 + clippingRect,
193.630 + this.MinimumSegmentLength * this.MinimumSegmentLength,
193.631 + this.GetSelectableColor(this.ActualColor),
193.632 + this.StrokeThickness,
193.633 + this.ActualLineStyle,
193.634 + this.LineJoin,
193.635 + false);
193.636 + }
193.637 +
193.638 + /// <summary>
193.639 + /// Force the smoothed points to be re-evaluated.
193.640 + /// </summary>
193.641 + protected void ResetSmoothedPoints()
193.642 + {
193.643 + double tolerance = Math.Abs(Math.Max(this.MaxX - this.MinX, this.MaxY - this.MinY) / ToleranceDivisor);
193.644 + this.smoothedPoints = CanonicalSplineHelper.CreateSpline(this.Points, 0.5, null, false, tolerance);
193.645 + }
193.646 + }
193.647 +}
193.648 \ No newline at end of file
194.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
194.2 +++ b/External/OxyPlot/OxyPlot/Series/PieSeries.cs Sat Jun 08 16:53:22 2013 +0000
194.3 @@ -0,0 +1,481 @@
194.4 +// --------------------------------------------------------------------------------------------------------------------
194.5 +// <copyright file="PieSeries.cs" company="OxyPlot">
194.6 +// The MIT License (MIT)
194.7 +//
194.8 +// Copyright (c) 2012 Oystein Bjorke
194.9 +//
194.10 +// Permission is hereby granted, free of charge, to any person obtaining a
194.11 +// copy of this software and associated documentation files (the
194.12 +// "Software"), to deal in the Software without restriction, including
194.13 +// without limitation the rights to use, copy, modify, merge, publish,
194.14 +// distribute, sublicense, and/or sell copies of the Software, and to
194.15 +// permit persons to whom the Software is furnished to do so, subject to
194.16 +// the following conditions:
194.17 +//
194.18 +// The above copyright notice and this permission notice shall be included
194.19 +// in all copies or substantial portions of the Software.
194.20 +//
194.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
194.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
194.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
194.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
194.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
194.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
194.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
194.28 +// </copyright>
194.29 +// <summary>
194.30 +// Represents a series for pie/circle/doughnut charts.
194.31 +// </summary>
194.32 +// --------------------------------------------------------------------------------------------------------------------
194.33 +namespace OxyPlot.Series
194.34 +{
194.35 + using System;
194.36 + using System.Collections.Generic;
194.37 + using System.Linq;
194.38 +
194.39 + using OxyPlot.Axes;
194.40 +
194.41 + /// <summary>
194.42 + /// Represents a series for pie/circle/doughnut charts.
194.43 + /// </summary>
194.44 + /// <remarks>
194.45 + /// The arc length/central angle/area of each slice is proportional to the quantity it represents. See http://en.wikipedia.org/wiki/Pie_chart
194.46 + /// </remarks>
194.47 + public class PieSeries : ItemsSeries
194.48 + {
194.49 + /// <summary>
194.50 + /// The slices.
194.51 + /// </summary>
194.52 + private IList<PieSlice> slices;
194.53 +
194.54 + /// <summary>
194.55 + /// Initializes a new instance of the <see cref="PieSeries"/> class.
194.56 + /// </summary>
194.57 + public PieSeries()
194.58 + {
194.59 + this.slices = new List<PieSlice>();
194.60 +
194.61 + this.Stroke = OxyColors.White;
194.62 + this.StrokeThickness = 1.0;
194.63 + this.Diameter = 1.0;
194.64 + this.InnerDiameter = 0.0;
194.65 + this.StartAngle = 0.0;
194.66 + this.AngleSpan = 360.0;
194.67 + this.AngleIncrement = 1.0;
194.68 +
194.69 + this.LegendFormat = null;
194.70 + this.OutsideLabelFormat = "{2:0} %";
194.71 + this.InsideLabelFormat = "{1}";
194.72 + this.TickDistance = 0;
194.73 + this.TickRadialLength = 6;
194.74 + this.TickHorizontalLength = 8;
194.75 + this.TickLabelDistance = 4;
194.76 + this.InsideLabelPosition = 0.5;
194.77 + this.FontSize = 12;
194.78 + }
194.79 +
194.80 + /// <summary>
194.81 + /// Gets or sets AngleIncrement.
194.82 + /// </summary>
194.83 + public double AngleIncrement { get; set; }
194.84 +
194.85 + /// <summary>
194.86 + /// Gets or sets AngleSpan.
194.87 + /// </summary>
194.88 + public double AngleSpan { get; set; }
194.89 +
194.90 + /// <summary>
194.91 + /// Gets or sets a value indicating whether AreInsideLabelsAngled.
194.92 + /// </summary>
194.93 + public bool AreInsideLabelsAngled { get; set; }
194.94 +
194.95 + /// <summary>
194.96 + /// Gets or sets the name of the property containing the color.
194.97 + /// </summary>
194.98 + /// <value> The color field. </value>
194.99 + public string ColorField { get; set; }
194.100 +
194.101 + /// <summary>
194.102 + /// Gets or sets the diameter.
194.103 + /// </summary>
194.104 + /// <value> The diameter. </value>
194.105 + public double Diameter { get; set; }
194.106 +
194.107 + /// <summary>
194.108 + /// Gets or sets the exploded distance.
194.109 + /// </summary>
194.110 + /// <value> The exploded distance. </value>
194.111 + public double ExplodedDistance { get; set; }
194.112 +
194.113 + /// <summary>
194.114 + /// Gets or sets the inner diameter.
194.115 + /// </summary>
194.116 + /// <value> The inner diameter. </value>
194.117 + public double InnerDiameter { get; set; }
194.118 +
194.119 + /// <summary>
194.120 + /// Gets or sets the inside label format.
194.121 + /// </summary>
194.122 + /// <value> The inside label format. </value>
194.123 + public string InsideLabelFormat { get; set; }
194.124 +
194.125 + /// <summary>
194.126 + /// Gets or sets the inside label position.
194.127 + /// </summary>
194.128 + /// <value> The inside label position. </value>
194.129 + public double InsideLabelPosition { get; set; }
194.130 +
194.131 + /// <summary>
194.132 + /// Gets or sets the is exploded field.
194.133 + /// </summary>
194.134 + /// <value> The is exploded field. </value>
194.135 + public string IsExplodedField { get; set; }
194.136 +
194.137 + /// <summary>
194.138 + /// Gets or sets the label field.
194.139 + /// </summary>
194.140 + /// <value> The label field. </value>
194.141 + public string LabelField { get; set; }
194.142 +
194.143 + /// <summary>
194.144 + /// Gets or sets the legend format.
194.145 + /// </summary>
194.146 + /// <value> The legend format. </value>
194.147 + public string LegendFormat { get; set; }
194.148 +
194.149 + /// <summary>
194.150 + /// Gets or sets the outside label format.
194.151 + /// </summary>
194.152 + /// <value> The outside label format. </value>
194.153 + public string OutsideLabelFormat { get; set; }
194.154 +
194.155 + /// <summary>
194.156 + /// Gets or sets the slices.
194.157 + /// </summary>
194.158 + /// <value> The slices. </value>
194.159 + public IList<PieSlice> Slices
194.160 + {
194.161 + get
194.162 + {
194.163 + return this.slices;
194.164 + }
194.165 +
194.166 + set
194.167 + {
194.168 + this.slices = value;
194.169 + }
194.170 + }
194.171 +
194.172 + /// <summary>
194.173 + /// Gets or sets the start angle.
194.174 + /// </summary>
194.175 + /// <value> The start angle. </value>
194.176 + public double StartAngle { get; set; }
194.177 +
194.178 + /// <summary>
194.179 + /// Gets or sets the stroke.
194.180 + /// </summary>
194.181 + /// <value> The stroke. </value>
194.182 + public OxyColor Stroke { get; set; }
194.183 +
194.184 + /// <summary>
194.185 + /// Gets or sets the stroke thickness.
194.186 + /// </summary>
194.187 + /// <value> The stroke thickness. </value>
194.188 + public double StrokeThickness { get; set; }
194.189 +
194.190 + /// <summary>
194.191 + /// Gets or sets the tick distance.
194.192 + /// </summary>
194.193 + /// <value> The tick distance. </value>
194.194 + public double TickDistance { get; set; }
194.195 +
194.196 + /// <summary>
194.197 + /// Gets or sets the length of the horizontal part of the tick.
194.198 + /// </summary>
194.199 + /// <value> The length. </value>
194.200 + public double TickHorizontalLength { get; set; }
194.201 +
194.202 + /// <summary>
194.203 + /// Gets or sets the tick label distance.
194.204 + /// </summary>
194.205 + /// <value> The tick label distance. </value>
194.206 + public double TickLabelDistance { get; set; }
194.207 +
194.208 + /// <summary>
194.209 + /// Gets or sets the length of the tick radial.
194.210 + /// </summary>
194.211 + /// <value> The length of the tick radial. </value>
194.212 + public double TickRadialLength { get; set; }
194.213 +
194.214 + /// <summary>
194.215 + /// Gets or sets the name of the property containing the value.
194.216 + /// </summary>
194.217 + /// <value> The value field. </value>
194.218 + public string ValueField { get; set; }
194.219 +
194.220 + /// <summary>
194.221 + /// Gets the point on the series that is nearest the specified point.
194.222 + /// </summary>
194.223 + /// <param name="point">
194.224 + /// The point.
194.225 + /// </param>
194.226 + /// <param name="interpolate">
194.227 + /// Interpolate the series if this flag is set to <c>true</c> .
194.228 + /// </param>
194.229 + /// <returns>
194.230 + /// A TrackerHitResult for the current hit.
194.231 + /// </returns>
194.232 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
194.233 + {
194.234 + return null;
194.235 + }
194.236 +
194.237 + /// <summary>
194.238 + /// Renders the series on the specified render context.
194.239 + /// </summary>
194.240 + /// <param name="rc">
194.241 + /// The rendering context.
194.242 + /// </param>
194.243 + /// <param name="model">
194.244 + /// The model.
194.245 + /// </param>
194.246 + public override void Render(IRenderContext rc, PlotModel model)
194.247 + {
194.248 + if (this.Slices.Count == 0)
194.249 + {
194.250 + return;
194.251 + }
194.252 +
194.253 + double total = this.slices.Sum(slice => slice.Value);
194.254 + if (Math.Abs(total) < double.Epsilon)
194.255 + {
194.256 + return;
194.257 + }
194.258 +
194.259 + // todo: reduce available size due to the labels
194.260 + double radius = Math.Min(model.PlotArea.Width, model.PlotArea.Height) / 2;
194.261 +
194.262 + double outerRadius = radius * (this.Diameter - this.ExplodedDistance);
194.263 + double innerRadius = radius * this.InnerDiameter;
194.264 +
194.265 + double angle = this.StartAngle;
194.266 + var midPoint = new ScreenPoint(
194.267 + (model.PlotArea.Left + model.PlotArea.Right) * 0.5, (model.PlotArea.Top + model.PlotArea.Bottom) * 0.5);
194.268 +
194.269 + foreach (var slice in this.slices)
194.270 + {
194.271 + var outerPoints = new List<ScreenPoint>();
194.272 + var innerPoints = new List<ScreenPoint>();
194.273 +
194.274 + double sliceAngle = slice.Value / total * this.AngleSpan;
194.275 + double endAngle = angle + sliceAngle;
194.276 + double explodedRadius = slice.IsExploded ? this.ExplodedDistance * radius : 0.0;
194.277 +
194.278 + double midAngle = angle + (sliceAngle / 2);
194.279 + double midAngleRadians = midAngle * Math.PI / 180;
194.280 + var mp = new ScreenPoint(
194.281 + midPoint.X + (explodedRadius * Math.Cos(midAngleRadians)),
194.282 + midPoint.Y + (explodedRadius * Math.Sin(midAngleRadians)));
194.283 +
194.284 + // Create the pie sector points for both outside and inside arcs
194.285 + while (true)
194.286 + {
194.287 + bool stop = false;
194.288 + if (angle >= endAngle)
194.289 + {
194.290 + angle = endAngle;
194.291 + stop = true;
194.292 + }
194.293 +
194.294 + double a = angle * Math.PI / 180;
194.295 + var op = new ScreenPoint(mp.X + (outerRadius * Math.Cos(a)), mp.Y + (outerRadius * Math.Sin(a)));
194.296 + outerPoints.Add(op);
194.297 + var ip = new ScreenPoint(mp.X + (innerRadius * Math.Cos(a)), mp.Y + (innerRadius * Math.Sin(a)));
194.298 + if (innerRadius + explodedRadius > 0)
194.299 + {
194.300 + innerPoints.Add(ip);
194.301 + }
194.302 +
194.303 + if (stop)
194.304 + {
194.305 + break;
194.306 + }
194.307 +
194.308 + angle += this.AngleIncrement;
194.309 + }
194.310 +
194.311 + innerPoints.Reverse();
194.312 + if (innerPoints.Count == 0)
194.313 + {
194.314 + innerPoints.Add(mp);
194.315 + }
194.316 +
194.317 + innerPoints.Add(outerPoints[0]);
194.318 +
194.319 + var points = outerPoints;
194.320 + points.AddRange(innerPoints);
194.321 +
194.322 + rc.DrawPolygon(points, slice.ActualFillColor, this.Stroke, this.StrokeThickness, null, OxyPenLineJoin.Bevel);
194.323 +
194.324 + // Render label outside the slice
194.325 + if (this.OutsideLabelFormat != null)
194.326 + {
194.327 + string label = string.Format(
194.328 + this.OutsideLabelFormat, slice.Value, slice.Label, slice.Value / total * 100);
194.329 + int sign = Math.Sign(Math.Cos(midAngleRadians));
194.330 +
194.331 + // tick points
194.332 + var tp0 = new ScreenPoint(
194.333 + mp.X + ((outerRadius + this.TickDistance) * Math.Cos(midAngleRadians)),
194.334 + mp.Y + ((outerRadius + this.TickDistance) * Math.Sin(midAngleRadians)));
194.335 + var tp1 = new ScreenPoint(
194.336 + tp0.X + (this.TickRadialLength * Math.Cos(midAngleRadians)),
194.337 + tp0.Y + (this.TickRadialLength * Math.Sin(midAngleRadians)));
194.338 + var tp2 = new ScreenPoint(tp1.X + (this.TickHorizontalLength * sign), tp1.Y);
194.339 + rc.DrawLine(new[] { tp0, tp1, tp2 }, this.Stroke, this.StrokeThickness, null, OxyPenLineJoin.Bevel);
194.340 +
194.341 + // label
194.342 + var labelPosition = new ScreenPoint(tp2.X + (this.TickLabelDistance * sign), tp2.Y);
194.343 + rc.DrawText(
194.344 + labelPosition,
194.345 + label,
194.346 + this.ActualTextColor,
194.347 + this.ActualFont,
194.348 + this.ActualFontSize,
194.349 + this.ActualFontWeight,
194.350 + 0,
194.351 + sign > 0 ? HorizontalAlignment.Left : HorizontalAlignment.Right,
194.352 + VerticalAlignment.Middle);
194.353 + }
194.354 +
194.355 + // Render label inside the slice
194.356 + if (this.InsideLabelFormat != null)
194.357 + {
194.358 + string label = string.Format(
194.359 + this.InsideLabelFormat, slice.Value, slice.Label, slice.Value / total * 100);
194.360 + double r = (innerRadius * (1 - this.InsideLabelPosition)) + (outerRadius * this.InsideLabelPosition);
194.361 + var labelPosition = new ScreenPoint(
194.362 + mp.X + (r * Math.Cos(midAngleRadians)), mp.Y + (r * Math.Sin(midAngleRadians)));
194.363 + double textAngle = 0;
194.364 + if (this.AreInsideLabelsAngled)
194.365 + {
194.366 + textAngle = midAngle;
194.367 + if (Math.Cos(midAngleRadians) < 0)
194.368 + {
194.369 + textAngle += 180;
194.370 + }
194.371 + }
194.372 +
194.373 + rc.DrawText(
194.374 + labelPosition,
194.375 + label,
194.376 + this.ActualTextColor,
194.377 + this.ActualFont,
194.378 + this.ActualFontSize,
194.379 + this.ActualFontWeight,
194.380 + textAngle,
194.381 + HorizontalAlignment.Center,
194.382 + VerticalAlignment.Middle);
194.383 + }
194.384 + }
194.385 + }
194.386 +
194.387 + /// <summary>
194.388 + /// Renders the legend symbol on the specified render context.
194.389 + /// </summary>
194.390 + /// <param name="rc">
194.391 + /// The rendering context.
194.392 + /// </param>
194.393 + /// <param name="legendBox">
194.394 + /// The legend rectangle.
194.395 + /// </param>
194.396 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
194.397 + {
194.398 + }
194.399 +
194.400 + /// <summary>
194.401 + /// Check if this data series requires X/Y axes. (e.g. Pie series do not require axes)
194.402 + /// </summary>
194.403 + /// <returns>
194.404 + /// True if no axes are required.
194.405 + /// </returns>
194.406 + protected internal override bool AreAxesRequired()
194.407 + {
194.408 + return false;
194.409 + }
194.410 +
194.411 + /// <summary>
194.412 + /// Ensures that the axes of the series is defined.
194.413 + /// </summary>
194.414 + protected internal override void EnsureAxes()
194.415 + {
194.416 + }
194.417 +
194.418 + /// <summary>
194.419 + /// Check if the data series is using the specified axis.
194.420 + /// </summary>
194.421 + /// <param name="axis">
194.422 + /// An axis.
194.423 + /// </param>
194.424 + /// <returns>
194.425 + /// True if the axis is in use.
194.426 + /// </returns>
194.427 + protected internal override bool IsUsing(Axis axis)
194.428 + {
194.429 + return false;
194.430 + }
194.431 +
194.432 + /// <summary>
194.433 + /// The set default values.
194.434 + /// </summary>
194.435 + /// <param name="model">
194.436 + /// The model.
194.437 + /// </param>
194.438 + protected internal override void SetDefaultValues(PlotModel model)
194.439 + {
194.440 + foreach (var slice in this.Slices)
194.441 + {
194.442 + if (slice.Fill == null)
194.443 + {
194.444 + slice.DefaultFillColor = model.GetDefaultColor();
194.445 + }
194.446 + }
194.447 + }
194.448 +
194.449 + /// <summary>
194.450 + /// The update axis max min.
194.451 + /// </summary>
194.452 + protected internal override void UpdateAxisMaxMin()
194.453 + {
194.454 + }
194.455 +
194.456 + /// <summary>
194.457 + /// Updates the data.
194.458 + /// </summary>
194.459 + protected internal override void UpdateData()
194.460 + {
194.461 + if (this.ItemsSource == null)
194.462 + {
194.463 + return;
194.464 + }
194.465 +
194.466 + this.slices.Clear();
194.467 +
194.468 + var filler = new ListFiller<PieSlice>();
194.469 + filler.Add(this.LabelField, (item, value) => item.Label = Convert.ToString(value));
194.470 + filler.Add(this.ValueField, (item, value) => item.Value = Convert.ToDouble(value));
194.471 + filler.Add(this.ColorField, (item, value) => item.Fill = (OxyColor)value);
194.472 + filler.Add(this.IsExplodedField, (item, value) => item.IsExploded = (bool)value);
194.473 + filler.FillT(this.slices, this.ItemsSource);
194.474 + }
194.475 +
194.476 + /// <summary>
194.477 + /// The update max min.
194.478 + /// </summary>
194.479 + protected internal override void UpdateMaxMin()
194.480 + {
194.481 + }
194.482 +
194.483 + }
194.484 +}
194.485 \ No newline at end of file
195.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
195.2 +++ b/External/OxyPlot/OxyPlot/Series/PieSlice.cs Sat Jun 08 16:53:22 2013 +0000
195.3 @@ -0,0 +1,99 @@
195.4 +// --------------------------------------------------------------------------------------------------------------------
195.5 +// <copyright file="PieSlice.cs" company="OxyPlot">
195.6 +// The MIT License (MIT)
195.7 +//
195.8 +// Copyright (c) 2012 Oystein Bjorke
195.9 +//
195.10 +// Permission is hereby granted, free of charge, to any person obtaining a
195.11 +// copy of this software and associated documentation files (the
195.12 +// "Software"), to deal in the Software without restriction, including
195.13 +// without limitation the rights to use, copy, modify, merge, publish,
195.14 +// distribute, sublicense, and/or sell copies of the Software, and to
195.15 +// permit persons to whom the Software is furnished to do so, subject to
195.16 +// the following conditions:
195.17 +//
195.18 +// The above copyright notice and this permission notice shall be included
195.19 +// in all copies or substantial portions of the Software.
195.20 +//
195.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
195.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
195.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
195.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
195.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
195.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
195.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
195.28 +// </copyright>
195.29 +// <summary>
195.30 +// Represent a slice of a PieSeries.
195.31 +// </summary>
195.32 +// --------------------------------------------------------------------------------------------------------------------
195.33 +namespace OxyPlot.Series
195.34 +{
195.35 + /// <summary>
195.36 + /// Represent a slice of a <see cref="PieSeries"/>.
195.37 + /// </summary>
195.38 + public class PieSlice
195.39 + {
195.40 + /// <summary>
195.41 + /// Initializes a new instance of the <see cref = "PieSlice" /> class.
195.42 + /// </summary>
195.43 + public PieSlice()
195.44 + {
195.45 + }
195.46 +
195.47 + /// <summary>
195.48 + /// Initializes a new instance of the <see cref="PieSlice"/> class.
195.49 + /// </summary>
195.50 + /// <param name="label">
195.51 + /// The label.
195.52 + /// </param>
195.53 + /// <param name="value">
195.54 + /// The value.
195.55 + /// </param>
195.56 + /// <param name="fill">
195.57 + /// The fill.
195.58 + /// </param>
195.59 + public PieSlice(string label, double value, OxyColor fill = null)
195.60 + {
195.61 + this.Label = label;
195.62 + this.Value = value;
195.63 + this.Fill = fill;
195.64 + }
195.65 +
195.66 + /// <summary>
195.67 + /// Gets or sets Fill.
195.68 + /// </summary>
195.69 + public OxyColor Fill { get; set; }
195.70 +
195.71 + /// <summary>
195.72 + /// Gets the actual fill color.
195.73 + /// </summary>
195.74 + /// <value>The actual color.</value>
195.75 + public OxyColor ActualFillColor
195.76 + {
195.77 + get { return this.Fill ?? this.DefaultFillColor; }
195.78 + }
195.79 +
195.80 + /// <summary>
195.81 + /// Gets or sets a value indicating whether IsExploded.
195.82 + /// </summary>
195.83 + public bool IsExploded { get; set; }
195.84 +
195.85 + /// <summary>
195.86 + /// Gets or sets Label.
195.87 + /// </summary>
195.88 + public string Label { get; set; }
195.89 +
195.90 + /// <summary>
195.91 + /// Gets or sets Value.
195.92 + /// </summary>
195.93 + public double Value { get; set; }
195.94 +
195.95 + /// <summary>
195.96 + /// Gets or sets the default fill color.
195.97 + /// </summary>
195.98 + /// <value>The default fill color.</value>
195.99 + internal OxyColor DefaultFillColor { get; set; }
195.100 +
195.101 + }
195.102 +}
195.103 \ No newline at end of file
196.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
196.2 +++ b/External/OxyPlot/OxyPlot/Series/PlotSeriesBase.cs Sat Jun 08 16:53:22 2013 +0000
196.3 @@ -0,0 +1,302 @@
196.4 +// --------------------------------------------------------------------------------------------------------------------
196.5 +// <copyright file="PlotSeriesBase.cs" company="OxyPlot">
196.6 +// The MIT License (MIT)
196.7 +//
196.8 +// Copyright (c) 2012 Oystein Bjorke
196.9 +//
196.10 +// Permission is hereby granted, free of charge, to any person obtaining a
196.11 +// copy of this software and associated documentation files (the
196.12 +// "Software"), to deal in the Software without restriction, including
196.13 +// without limitation the rights to use, copy, modify, merge, publish,
196.14 +// distribute, sublicense, and/or sell copies of the Software, and to
196.15 +// permit persons to whom the Software is furnished to do so, subject to
196.16 +// the following conditions:
196.17 +//
196.18 +// The above copyright notice and this permission notice shall be included
196.19 +// in all copies or substantial portions of the Software.
196.20 +//
196.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
196.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
196.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
196.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
196.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
196.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
196.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
196.28 +// </copyright>
196.29 +// <summary>
196.30 +// Abstract base class for Series that contains an X-axis and Y-axis
196.31 +// </summary>
196.32 +// --------------------------------------------------------------------------------------------------------------------
196.33 +namespace OxyPlot
196.34 +{
196.35 + using System;
196.36 + using System.Collections;
196.37 + using System.Collections.Generic;
196.38 + using System.Collections.ObjectModel;
196.39 + using System.Linq;
196.40 +
196.41 + /// <summary>
196.42 + /// Abstract base class for Series that contains an X-axis and Y-axis
196.43 + /// </summary>
196.44 + public abstract class PlotSeriesBase : ItemsSeries
196.45 + {
196.46 + /// <summary>
196.47 + /// Gets or sets the maximum x-coordinate of the dataset.
196.48 + /// </summary>
196.49 + /// <value>The maximum x-coordinate.</value>
196.50 + public double MaxX { get; protected set; }
196.51 +
196.52 + /// <summary>
196.53 + /// Gets or sets the maximum y-coordinate of the dataset.
196.54 + /// </summary>
196.55 + /// <value>The maximum y-coordinate.</value>
196.56 + public double MaxY { get; protected set; }
196.57 +
196.58 + /// <summary>
196.59 + /// Gets or sets the minimum x-coordinate of the dataset.
196.60 + /// </summary>
196.61 + /// <value>The minimum x-coordinate.</value>
196.62 + public double MinX { get; protected set; }
196.63 +
196.64 + /// <summary>
196.65 + /// Gets or sets the minimum y-coordinate of the dataset.
196.66 + /// </summary>
196.67 + /// <value>The minimum y-coordinate.</value>
196.68 + public double MinY { get; protected set; }
196.69 +
196.70 + /// <summary>
196.71 + /// Gets or sets the x-axis.
196.72 + /// </summary>
196.73 + /// <value>The x-axis.</value>
196.74 + public IAxis XAxis { get; set; }
196.75 +
196.76 + /// <summary>
196.77 + /// Gets or sets the x-axis key.
196.78 + /// </summary>
196.79 + /// <value>The x-axis key.</value>
196.80 + public string XAxisKey { get; set; }
196.81 +
196.82 + /// <summary>
196.83 + /// Gets or sets the y-axis.
196.84 + /// </summary>
196.85 + /// <value>The y-axis.</value>
196.86 + public IAxis YAxis { get; set; }
196.87 +
196.88 + /// <summary>
196.89 + /// Gets or sets the y-axis key.
196.90 + /// </summary>
196.91 + /// <value>The y-axis key.</value>
196.92 + public string YAxisKey { get; set; }
196.93 +
196.94 + /// <summary>
196.95 + /// Check if this data series requires X/Y axes.
196.96 + /// (e.g. Pie series do not require axes)
196.97 + /// </summary>
196.98 + /// <returns></returns>
196.99 + public override bool AreAxesRequired()
196.100 + {
196.101 + return true;
196.102 + }
196.103 +
196.104 + public override void EnsureAxes(Collection<IAxis> axes, IAxis defaultXAxis, IAxis defaultYAxis)
196.105 + {
196.106 + if (this.XAxisKey != null)
196.107 + {
196.108 + this.XAxis = axes.FirstOrDefault(a => a.Key == this.XAxisKey);
196.109 + }
196.110 +
196.111 + if (this.YAxisKey != null)
196.112 + {
196.113 + this.YAxis = axes.FirstOrDefault(a => a.Key == this.YAxisKey);
196.114 + }
196.115 +
196.116 + // If axes are not found, use the default axes
196.117 + if (this.XAxis == null)
196.118 + {
196.119 + this.XAxis = defaultXAxis;
196.120 + }
196.121 +
196.122 + if (this.YAxis == null)
196.123 + {
196.124 + this.YAxis = defaultYAxis;
196.125 + }
196.126 + }
196.127 +
196.128 + /// <summary>
196.129 + /// Gets the rectangle the series uses on the screen (screen coordinates).
196.130 + /// </summary>
196.131 + /// <returns></returns>
196.132 + public OxyRect GetScreenRectangle()
196.133 + {
196.134 + return this.GetClippingRect();
196.135 + }
196.136 +
196.137 + public override bool IsUsing(IAxis axis)
196.138 + {
196.139 + return this.XAxis == axis || this.YAxis == axis;
196.140 + }
196.141 +
196.142 + /// <summary>
196.143 + /// Renders the Series on the specified rendering context.
196.144 + /// </summary>
196.145 + /// <param name = "rc">The rendering context.</param>
196.146 + /// <param name = "model">The model.</param>
196.147 + public override void Render(IRenderContext rc, PlotModel model)
196.148 + {
196.149 + }
196.150 +
196.151 + /// <summary>
196.152 + /// Renders the legend symbol on the specified rendering context.
196.153 + /// </summary>
196.154 + /// <param name = "rc">The rendering context.</param>
196.155 + /// <param name = "legendBox">The legend rectangle.</param>
196.156 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
196.157 + {
196.158 + }
196.159 +
196.160 + public override void SetDefaultValues(PlotModel model)
196.161 + {
196.162 + }
196.163 +
196.164 + public override void UpdateData()
196.165 + {
196.166 + }
196.167 +
196.168 + /// <summary>
196.169 + /// Updates the max/minimum values.
196.170 + /// </summary>
196.171 + public override void UpdateMaxMin()
196.172 + {
196.173 + this.MinX = this.MinY = this.MaxX = this.MaxY = double.NaN;
196.174 + }
196.175 +
196.176 + protected OxyRect GetClippingRect()
196.177 + {
196.178 + double minX = Math.Min(this.XAxis.ScreenMin.X, this.XAxis.ScreenMax.X);
196.179 + double minY = Math.Min(this.YAxis.ScreenMin.Y, this.YAxis.ScreenMax.Y);
196.180 + double maxX = Math.Max(this.XAxis.ScreenMin.X, this.XAxis.ScreenMax.X);
196.181 + double maxY = Math.Max(this.YAxis.ScreenMin.Y, this.YAxis.ScreenMax.Y);
196.182 +
196.183 + return new OxyRect(minX, minY, maxX - minX, maxY - minY);
196.184 + }
196.185 +
196.186 + /// <summary>
196.187 + /// Gets the point on the curve that is nearest the specified point.
196.188 + /// </summary>
196.189 + /// <param name = "point">The point.</param>
196.190 + /// <param name = "dpn">The nearest point (data coordinates).</param>
196.191 + /// <param name = "spn">The nearest point (screen coordinates).</param>
196.192 + /// <returns></returns>
196.193 + protected bool GetNearestInterpolatedPointInternal(
196.194 + IList<IDataPoint> points, ScreenPoint point, out DataPoint dpn, out ScreenPoint spn, out int index)
196.195 + {
196.196 + spn = default(ScreenPoint);
196.197 + dpn = default(DataPoint);
196.198 + index = -1;
196.199 +
196.200 + // http://local.wasp.uwa.edu.au/~pbourke/geometry/pointline/
196.201 + double minimumDistance = double.MaxValue;
196.202 +
196.203 + for (int i = 0; i + 1 < points.Count; i++)
196.204 + {
196.205 + IDataPoint p1 = points[i];
196.206 + IDataPoint p2 = points[i + 1];
196.207 + ScreenPoint sp1 = AxisBase.Transform(p1, this.XAxis, this.YAxis);
196.208 + ScreenPoint sp2 = AxisBase.Transform(p2, this.XAxis, this.YAxis);
196.209 +
196.210 + double sp21X = sp2.x - sp1.x;
196.211 + double sp21Y = sp2.y - sp1.y;
196.212 + double u1 = (point.x - sp1.x) * sp21X + (point.y - sp1.y) * sp21Y;
196.213 + double u2 = sp21X * sp21X + sp21Y * sp21Y;
196.214 + double ds = sp21X * sp21X + sp21Y * sp21Y;
196.215 +
196.216 + if (ds < 4)
196.217 + {
196.218 + // if the points are very close, we can get numerical problems, just use the first point...
196.219 + u1 = 0;
196.220 + u2 = 1;
196.221 + }
196.222 +
196.223 + if (u2 < double.Epsilon && u2 > -double.Epsilon)
196.224 + {
196.225 + continue; // P1 && P2 coincident
196.226 + }
196.227 +
196.228 + double u = u1 / u2;
196.229 + if (u < 0) u = 0;
196.230 + if (u > 1) u = 1;
196.231 +
196.232 + double sx = sp1.x + u * sp21X;
196.233 + double sy = sp1.y + u * sp21Y;
196.234 +
196.235 + double dx = point.x - sx;
196.236 + double dy = point.y - sy;
196.237 + double distance = dx * dx + dy * dy;
196.238 +
196.239 + if (distance < minimumDistance)
196.240 + {
196.241 + double px = p1.X + u * (p2.X - p1.X);
196.242 + double py = p1.Y + u * (p2.Y - p1.Y);
196.243 + dpn = new DataPoint(px, py);
196.244 + spn = new ScreenPoint(sx, sy);
196.245 + minimumDistance = distance;
196.246 + index = i;
196.247 + }
196.248 + }
196.249 +
196.250 + return minimumDistance < double.MaxValue;
196.251 + }
196.252 +
196.253 + protected bool GetNearestPointInternal(
196.254 + IEnumerable<IDataPoint> points, ScreenPoint point, out DataPoint dpn, out ScreenPoint spn, out int index)
196.255 + {
196.256 + spn = default(ScreenPoint);
196.257 + dpn = default(DataPoint);
196.258 + index = -1;
196.259 +
196.260 + double minimumDistance = double.MaxValue;
196.261 + int i = 0;
196.262 + foreach (DataPoint p in points)
196.263 + {
196.264 + ScreenPoint sp = AxisBase.Transform(p, this.XAxis, this.YAxis);
196.265 + double dx = sp.x - point.x;
196.266 + double dy = sp.y - point.y;
196.267 + double d2 = dx * dx + dy * dy;
196.268 +
196.269 + if (d2 < minimumDistance)
196.270 + {
196.271 + dpn = p;
196.272 + spn = sp;
196.273 + minimumDistance = d2;
196.274 + index = i;
196.275 + }
196.276 + i++;
196.277 + }
196.278 +
196.279 + return minimumDistance < double.MaxValue;
196.280 + }
196.281 +
196.282 + /// <summary>
196.283 + /// Converts the value of the specified object to a double precision floating point number.
196.284 + /// DateTime objects are converted using DateTimeAxis.ToDouble
196.285 + /// TimeSpan objects are converted using TimeSpanAxis.ToDouble
196.286 + /// </summary>
196.287 + /// <param name="value">The value.</param>
196.288 + /// <returns></returns>
196.289 + protected virtual double ToDouble(object value)
196.290 + {
196.291 + if (value is DateTime)
196.292 + {
196.293 + return DateTimeAxis.ToDouble((DateTime)value);
196.294 + }
196.295 +
196.296 + if (value is TimeSpan)
196.297 + {
196.298 + return ((TimeSpan)value).TotalSeconds;
196.299 + }
196.300 +
196.301 + return Convert.ToDouble(value);
196.302 + }
196.303 +
196.304 + }
196.305 +}
196.306 \ No newline at end of file
197.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
197.2 +++ b/External/OxyPlot/OxyPlot/Series/ScatterPoint.cs Sat Jun 08 16:53:22 2013 +0000
197.3 @@ -0,0 +1,232 @@
197.4 +// --------------------------------------------------------------------------------------------------------------------
197.5 +// <copyright file="ScatterPoint.cs" company="OxyPlot">
197.6 +// The MIT License (MIT)
197.7 +//
197.8 +// Copyright (c) 2012 Oystein Bjorke
197.9 +//
197.10 +// Permission is hereby granted, free of charge, to any person obtaining a
197.11 +// copy of this software and associated documentation files (the
197.12 +// "Software"), to deal in the Software without restriction, including
197.13 +// without limitation the rights to use, copy, modify, merge, publish,
197.14 +// distribute, sublicense, and/or sell copies of the Software, and to
197.15 +// permit persons to whom the Software is furnished to do so, subject to
197.16 +// the following conditions:
197.17 +//
197.18 +// The above copyright notice and this permission notice shall be included
197.19 +// in all copies or substantial portions of the Software.
197.20 +//
197.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
197.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
197.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
197.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
197.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
197.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
197.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
197.28 +// </copyright>
197.29 +// <summary>
197.30 +// Represents a point in a ScatterSeries.
197.31 +// </summary>
197.32 +// --------------------------------------------------------------------------------------------------------------------
197.33 +namespace OxyPlot.Series
197.34 +{
197.35 + using System.Diagnostics.CodeAnalysis;
197.36 +
197.37 + /// <summary>
197.38 + /// Represents a point in a <see cref="ScatterSeries"/>.
197.39 + /// </summary>
197.40 + public class ScatterPoint : IDataPoint
197.41 + {
197.42 + // ReSharper disable InconsistentNaming
197.43 +
197.44 + /// <summary>
197.45 + /// The size.
197.46 + /// </summary>
197.47 + [SuppressMessage("StyleCop.CSharp.NamingRules", "SA1307:AccessibleFieldsMustBeginWithUpperCaseLetter", Justification = "Reviewed. Suppression is OK here.")]
197.48 + [SuppressMessage("StyleCop.CSharp.MaintainabilityRules", "SA1401:FieldsMustBePrivate", Justification = "Reviewed. Suppression is OK here.")]
197.49 + internal double size;
197.50 +
197.51 + /// <summary>
197.52 + /// The tag.
197.53 + /// </summary>
197.54 + [SuppressMessage("StyleCop.CSharp.NamingRules", "SA1307:AccessibleFieldsMustBeginWithUpperCaseLetter", Justification = "Reviewed. Suppression is OK here.")]
197.55 + [SuppressMessage("StyleCop.CSharp.MaintainabilityRules", "SA1401:FieldsMustBePrivate", Justification = "Reviewed. Suppression is OK here.")]
197.56 + internal object tag;
197.57 +
197.58 + /// <summary>
197.59 + /// The value.
197.60 + /// </summary>
197.61 + [SuppressMessage("StyleCop.CSharp.NamingRules", "SA1307:AccessibleFieldsMustBeginWithUpperCaseLetter", Justification = "Reviewed. Suppression is OK here.")]
197.62 + [SuppressMessage("StyleCop.CSharp.MaintainabilityRules", "SA1401:FieldsMustBePrivate", Justification = "Reviewed. Suppression is OK here.")]
197.63 + internal double value;
197.64 +
197.65 + /// <summary>
197.66 + /// The x.
197.67 + /// </summary>
197.68 + [SuppressMessage("StyleCop.CSharp.NamingRules", "SA1307:AccessibleFieldsMustBeginWithUpperCaseLetter", Justification = "Reviewed. Suppression is OK here.")]
197.69 + [SuppressMessage("StyleCop.CSharp.MaintainabilityRules", "SA1401:FieldsMustBePrivate", Justification = "Reviewed. Suppression is OK here.")]
197.70 + internal double x;
197.71 +
197.72 + /// <summary>
197.73 + /// The y.
197.74 + /// </summary>
197.75 + [SuppressMessage("StyleCop.CSharp.NamingRules", "SA1307:AccessibleFieldsMustBeginWithUpperCaseLetter", Justification = "Reviewed. Suppression is OK here.")]
197.76 + [SuppressMessage("StyleCop.CSharp.MaintainabilityRules", "SA1401:FieldsMustBePrivate", Justification = "Reviewed. Suppression is OK here.")]
197.77 + internal double y;
197.78 +
197.79 + // ReSharper restore InconsistentNaming
197.80 + /// <summary>
197.81 + /// Initializes a new instance of the <see cref="ScatterPoint"/> class.
197.82 + /// </summary>
197.83 + public ScatterPoint()
197.84 + {
197.85 + this.Size = double.NaN;
197.86 + this.Value = double.NaN;
197.87 + }
197.88 +
197.89 + /// <summary>
197.90 + /// Initializes a new instance of the <see cref="ScatterPoint"/> class.
197.91 + /// </summary>
197.92 + /// <param name="x">
197.93 + /// The x.
197.94 + /// </param>
197.95 + /// <param name="y">
197.96 + /// The y.
197.97 + /// </param>
197.98 + /// <param name="size">
197.99 + /// The size.
197.100 + /// </param>
197.101 + /// <param name="value">
197.102 + /// The value.
197.103 + /// </param>
197.104 + /// <param name="tag">
197.105 + /// The tag.
197.106 + /// </param>
197.107 + public ScatterPoint(double x, double y, double size = double.NaN, double value = double.NaN, object tag = null)
197.108 + {
197.109 + this.x = x;
197.110 + this.y = y;
197.111 + this.size = size;
197.112 + this.value = value;
197.113 + this.tag = tag;
197.114 + }
197.115 +
197.116 + /// <summary>
197.117 + /// Gets or sets the size.
197.118 + /// </summary>
197.119 + /// <value>The size.</value>
197.120 + public double Size
197.121 + {
197.122 + get
197.123 + {
197.124 + return this.size;
197.125 + }
197.126 +
197.127 + set
197.128 + {
197.129 + this.size = value;
197.130 + }
197.131 + }
197.132 +
197.133 + /// <summary>
197.134 + /// Gets or sets the tag.
197.135 + /// </summary>
197.136 + /// <value>The tag.</value>
197.137 + public object Tag
197.138 + {
197.139 + get
197.140 + {
197.141 + return this.tag;
197.142 + }
197.143 +
197.144 + set
197.145 + {
197.146 + this.tag = value;
197.147 + }
197.148 + }
197.149 +
197.150 + /// <summary>
197.151 + /// Gets or sets the value.
197.152 + /// </summary>
197.153 + /// <value>The value.</value>
197.154 + public double Value
197.155 + {
197.156 + get
197.157 + {
197.158 + return this.value;
197.159 + }
197.160 +
197.161 + set
197.162 + {
197.163 + this.value = value;
197.164 + }
197.165 + }
197.166 +
197.167 + /// <summary>
197.168 + /// Gets or sets the X.
197.169 + /// </summary>
197.170 + /// <value>The X.</value>
197.171 + public double X
197.172 + {
197.173 + get
197.174 + {
197.175 + return this.x;
197.176 + }
197.177 +
197.178 + set
197.179 + {
197.180 + this.x = value;
197.181 + }
197.182 + }
197.183 +
197.184 + /// <summary>
197.185 + /// Gets or sets the Y.
197.186 + /// </summary>
197.187 + /// <value>The Y.</value>
197.188 + public double Y
197.189 + {
197.190 + get
197.191 + {
197.192 + return this.y;
197.193 + }
197.194 +
197.195 + set
197.196 + {
197.197 + this.y = value;
197.198 + }
197.199 + }
197.200 +
197.201 + /// <summary>
197.202 + /// Returns C# code that generates this instance.
197.203 + /// </summary>
197.204 + /// <returns>
197.205 + /// C# code.
197.206 + /// </returns>
197.207 + public string ToCode()
197.208 + {
197.209 + if (double.IsNaN(this.size) && double.IsNaN(this.value))
197.210 + {
197.211 + return CodeGenerator.FormatConstructor(this.GetType(), "{0}, {1}", this.x, this.y);
197.212 + }
197.213 +
197.214 + if (double.IsNaN(this.value))
197.215 + {
197.216 + return CodeGenerator.FormatConstructor(this.GetType(), "{0}, {1}, {2}", this.x, this.y, this.size);
197.217 + }
197.218 +
197.219 + return CodeGenerator.FormatConstructor(
197.220 + this.GetType(), "{0}, {1}, {2}, {3}", this.x, this.y, this.size, this.value);
197.221 + }
197.222 +
197.223 + /// <summary>
197.224 + /// Returns a <see cref="System.String"/> that represents this instance.
197.225 + /// </summary>
197.226 + /// <returns>
197.227 + /// A <see cref="System.String"/> that represents this instance.
197.228 + /// </returns>
197.229 + public override string ToString()
197.230 + {
197.231 + return this.x + " " + this.y;
197.232 + }
197.233 +
197.234 + }
197.235 +}
197.236 \ No newline at end of file
198.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
198.2 +++ b/External/OxyPlot/OxyPlot/Series/ScatterSeries.cs Sat Jun 08 16:53:22 2013 +0000
198.3 @@ -0,0 +1,621 @@
198.4 +// --------------------------------------------------------------------------------------------------------------------
198.5 +// <copyright file="ScatterSeries.cs" company="OxyPlot">
198.6 +// The MIT License (MIT)
198.7 +//
198.8 +// Copyright (c) 2012 Oystein Bjorke
198.9 +//
198.10 +// Permission is hereby granted, free of charge, to any person obtaining a
198.11 +// copy of this software and associated documentation files (the
198.12 +// "Software"), to deal in the Software without restriction, including
198.13 +// without limitation the rights to use, copy, modify, merge, publish,
198.14 +// distribute, sublicense, and/or sell copies of the Software, and to
198.15 +// permit persons to whom the Software is furnished to do so, subject to
198.16 +// the following conditions:
198.17 +//
198.18 +// The above copyright notice and this permission notice shall be included
198.19 +// in all copies or substantial portions of the Software.
198.20 +//
198.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
198.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
198.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
198.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
198.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
198.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
198.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
198.28 +// </copyright>
198.29 +// <summary>
198.30 +// Represents a series for scatter plots.
198.31 +// </summary>
198.32 +// --------------------------------------------------------------------------------------------------------------------
198.33 +
198.34 +namespace OxyPlot.Series
198.35 +{
198.36 + using System;
198.37 + using System.Collections;
198.38 + using System.Collections.Generic;
198.39 +
198.40 + using OxyPlot.Axes;
198.41 +
198.42 + /// <summary>
198.43 + /// Represents a series for scatter plots.
198.44 + /// </summary>
198.45 + /// <remarks>
198.46 + /// See http://en.wikipedia.org/wiki/Scatter_plot
198.47 + /// </remarks>
198.48 + public class ScatterSeries : DataPointSeries
198.49 + {
198.50 + /// <summary>
198.51 + /// The default fill color.
198.52 + /// </summary>
198.53 + private OxyColor defaultMarkerFillColor;
198.54 +
198.55 + /// <summary>
198.56 + /// Initializes a new instance of the <see cref="ScatterSeries"/> class.
198.57 + /// </summary>
198.58 + /// <param name="title">
198.59 + /// The title.
198.60 + /// </param>
198.61 + /// <param name="markerFill">
198.62 + /// The marker fill color.
198.63 + /// </param>
198.64 + /// <param name="markerSize">
198.65 + /// Size of the markers (If ScatterPoint.Size is set, this value will be overridden).
198.66 + /// </param>
198.67 + public ScatterSeries(string title, OxyColor markerFill = null, double markerSize = 5)
198.68 + : this()
198.69 + {
198.70 + this.MarkerFill = markerFill;
198.71 + this.MarkerSize = markerSize;
198.72 + this.Title = title;
198.73 + }
198.74 +
198.75 + /// <summary>
198.76 + /// Initializes a new instance of the <see cref="ScatterSeries"/> class.
198.77 + /// </summary>
198.78 + public ScatterSeries()
198.79 + {
198.80 + this.DataFieldSize = null;
198.81 + this.DataFieldValue = null;
198.82 +
198.83 + this.MarkerFill = null;
198.84 + this.MarkerSize = 5;
198.85 + this.MarkerType = MarkerType.Square;
198.86 + this.MarkerStroke = null;
198.87 + this.MarkerStrokeThickness = 1.0;
198.88 + }
198.89 +
198.90 + /// <summary>
198.91 + /// Gets or sets the screen resolution. If this number is greater than 1, bins of that size is created for both x and y directions. Only one point will be drawn in each bin.
198.92 + /// </summary>
198.93 + public int BinSize { get; set; }
198.94 +
198.95 + /// <summary>
198.96 + /// Gets or sets the color map.
198.97 + /// </summary>
198.98 + /// <value> The color map. </value>
198.99 + /// <remarks>
198.100 + /// This is used to map scatter point values to colors.
198.101 + /// </remarks>
198.102 + public ColorAxis ColorAxis { get; set; }
198.103 +
198.104 + /// <summary>
198.105 + /// Gets or sets the color axis key.
198.106 + /// </summary>
198.107 + /// <value> The color axis key. </value>
198.108 + public string ColorAxisKey { get; set; }
198.109 +
198.110 + /// <summary>
198.111 + /// Gets or sets the data field for the size.
198.112 + /// </summary>
198.113 + /// <value> The size data field. </value>
198.114 + public string DataFieldSize { get; set; }
198.115 +
198.116 + /// <summary>
198.117 + /// Gets or sets the tag data field.
198.118 + /// </summary>
198.119 + /// <value> The tag data field. </value>
198.120 + public string DataFieldTag { get; set; }
198.121 +
198.122 + /// <summary>
198.123 + /// Gets or sets the value data field.
198.124 + /// </summary>
198.125 + /// <value> The value data field. </value>
198.126 + public string DataFieldValue { get; set; }
198.127 +
198.128 + /// <summary>
198.129 + /// Gets or sets the marker fill color. If null, this color will be automatically set.
198.130 + /// </summary>
198.131 + /// <value> The marker fill color. </value>
198.132 + public OxyColor MarkerFill { get; set; }
198.133 +
198.134 + /// <summary>
198.135 + /// Gets the actual fill color.
198.136 + /// </summary>
198.137 + /// <value>The actual color.</value>
198.138 + public OxyColor ActualMarkerFillColor
198.139 + {
198.140 + get { return this.MarkerFill ?? this.defaultMarkerFillColor; }
198.141 + }
198.142 +
198.143 + /// <summary>
198.144 + /// Gets or sets the marker outline polygon. Set MarkerType to Custom to use this.
198.145 + /// </summary>
198.146 + /// <value> The marker outline. </value>
198.147 + public ScreenPoint[] MarkerOutline { get; set; }
198.148 +
198.149 + /// <summary>
198.150 + /// Gets or sets the size of the marker (same size for all items).
198.151 + /// </summary>
198.152 + /// <value> The size of the markers. </value>
198.153 + public double MarkerSize { get; set; }
198.154 +
198.155 + /// <summary>
198.156 + /// Gets or sets the marker stroke.
198.157 + /// </summary>
198.158 + /// <value> The marker stroke. </value>
198.159 + public OxyColor MarkerStroke { get; set; }
198.160 +
198.161 + /// <summary>
198.162 + /// Gets or sets the marker stroke thickness.
198.163 + /// </summary>
198.164 + /// <value> The marker stroke thickness. </value>
198.165 + public double MarkerStrokeThickness { get; set; }
198.166 +
198.167 + /// <summary>
198.168 + /// Gets or sets the type of the marker.
198.169 + /// </summary>
198.170 + /// <value> The type of the marker. </value>
198.171 + /// <remarks>
198.172 + /// If MarkerType.Custom is used, the MarkerOutline property must be specified.
198.173 + /// </remarks>
198.174 + public MarkerType MarkerType { get; set; }
198.175 +
198.176 + /// <summary>
198.177 + /// Gets the max value of the points.
198.178 + /// </summary>
198.179 + public double MaxValue { get; private set; }
198.180 +
198.181 + /// <summary>
198.182 + /// Gets the min value of the points.
198.183 + /// </summary>
198.184 + public double MinValue { get; private set; }
198.185 +
198.186 + /// <summary>
198.187 + /// Gets the nearest point.
198.188 + /// </summary>
198.189 + /// <param name="point">
198.190 + /// The point.
198.191 + /// </param>
198.192 + /// <param name="interpolate">
198.193 + /// interpolate if set to <c>true</c> .
198.194 + /// </param>
198.195 + /// <returns>
198.196 + /// A TrackerHitResult for the current hit.
198.197 + /// </returns>
198.198 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
198.199 + {
198.200 + if (this.XAxis == null || this.YAxis == null)
198.201 + {
198.202 + return null;
198.203 + }
198.204 +
198.205 + if (interpolate)
198.206 + {
198.207 + return null;
198.208 + }
198.209 +
198.210 + TrackerHitResult result = null;
198.211 + double minimumDistance = double.MaxValue;
198.212 + int i = 0;
198.213 +
198.214 + var xaxisTitle = this.XAxis.Title ?? "X";
198.215 + var yaxisTitle = this.YAxis.Title ?? "Y";
198.216 + var colorAxisTitle = (this.ColorAxis != null ? this.ColorAxis.Title : null) ?? "Z";
198.217 +
198.218 + var formatString = TrackerFormatString;
198.219 + if (string.IsNullOrEmpty(this.TrackerFormatString))
198.220 + {
198.221 + // Create a default format string
198.222 + formatString = "{1}: {2}\n{3}: {4}";
198.223 + if (this.ColorAxis != null)
198.224 + {
198.225 + formatString += "\n{5}: {6}";
198.226 + }
198.227 + }
198.228 +
198.229 + foreach (var p in this.Points)
198.230 + {
198.231 + if (p.X < this.XAxis.ActualMinimum || p.X > this.XAxis.ActualMaximum || p.Y < this.YAxis.ActualMinimum || p.Y > this.YAxis.ActualMaximum)
198.232 + {
198.233 + i++;
198.234 + continue;
198.235 + }
198.236 +
198.237 + var dp = new DataPoint(p.X, p.Y);
198.238 + var sp = Axis.Transform(dp, this.XAxis, this.YAxis);
198.239 + double dx = sp.x - point.x;
198.240 + double dy = sp.y - point.y;
198.241 + double d2 = (dx * dx) + (dy * dy);
198.242 +
198.243 + if (d2 < minimumDistance)
198.244 + {
198.245 + var item = this.GetItem(i);
198.246 +
198.247 + object xvalue = this.XAxis.GetValue(dp.X);
198.248 + object yvalue = this.YAxis.GetValue(dp.Y);
198.249 + object zvalue = null;
198.250 +
198.251 + var scatterPoint = p as ScatterPoint;
198.252 + if (scatterPoint != null)
198.253 + {
198.254 + if (!double.IsNaN(scatterPoint.Value) && !double.IsInfinity(scatterPoint.Value))
198.255 + {
198.256 + zvalue = scatterPoint.Value;
198.257 + }
198.258 + }
198.259 +
198.260 + var text = StringHelper.Format(
198.261 + this.ActualCulture,
198.262 + formatString,
198.263 + item,
198.264 + this.Title,
198.265 + xaxisTitle,
198.266 + xvalue,
198.267 + yaxisTitle,
198.268 + yvalue,
198.269 + colorAxisTitle,
198.270 + zvalue);
198.271 +
198.272 + result = new TrackerHitResult(this, dp, sp, item, i, text);
198.273 +
198.274 + minimumDistance = d2;
198.275 + }
198.276 +
198.277 + i++;
198.278 + }
198.279 +
198.280 + return result;
198.281 + }
198.282 +
198.283 + /// <summary>
198.284 + /// Determines whether the specified point is valid.
198.285 + /// </summary>
198.286 + /// <param name="pt">
198.287 + /// The point.
198.288 + /// </param>
198.289 + /// <param name="xaxis">
198.290 + /// The x axis.
198.291 + /// </param>
198.292 + /// <param name="yaxis">
198.293 + /// The y axis.
198.294 + /// </param>
198.295 + /// <returns>
198.296 + /// <c>true</c> if the point is valid; otherwise, <c>false</c> .
198.297 + /// </returns>
198.298 + public virtual bool IsValidPoint(ScatterPoint pt, Axis xaxis, Axis yaxis)
198.299 + {
198.300 + return !double.IsNaN(pt.X) && !double.IsInfinity(pt.X) && !double.IsNaN(pt.Y) && !double.IsInfinity(pt.Y)
198.301 + && (xaxis != null && xaxis.IsValidValue(pt.X)) && (yaxis != null && yaxis.IsValidValue(pt.Y));
198.302 + }
198.303 +
198.304 + /// <summary>
198.305 + /// Renders the series on the specified rendering context.
198.306 + /// </summary>
198.307 + /// <param name="rc">
198.308 + /// The rendering context.
198.309 + /// </param>
198.310 + /// <param name="model">
198.311 + /// The owner plot model.
198.312 + /// </param>
198.313 + public override void Render(IRenderContext rc, PlotModel model)
198.314 + {
198.315 + if (this.Points.Count == 0)
198.316 + {
198.317 + return;
198.318 + }
198.319 +
198.320 + OxyRect clippingRect = this.GetClippingRect();
198.321 +
198.322 + var points = this.Points;
198.323 + int n = points.Count;
198.324 + var groupPoints = new Dictionary<int, IList<ScreenPoint>>();
198.325 + var groupSizes = new Dictionary<int, IList<double>>();
198.326 +
198.327 + ScreenPoint[] allPoints = null;
198.328 + double[] markerSizes = null;
198.329 +
198.330 + if (this.ColorAxis == null)
198.331 + {
198.332 + allPoints = new ScreenPoint[n];
198.333 + markerSizes = new double[n];
198.334 + }
198.335 +
198.336 + // Transform all points to screen coordinates
198.337 + for (int i = 0; i < n; i++)
198.338 + {
198.339 + var dp = new DataPoint(points[i].X, points[i].Y);
198.340 + double size = double.NaN;
198.341 + double value = double.NaN;
198.342 +
198.343 + var scatterPoint = points[i] as ScatterPoint;
198.344 + if (scatterPoint != null)
198.345 + {
198.346 + size = scatterPoint.Size;
198.347 + value = scatterPoint.Value;
198.348 + }
198.349 +
198.350 + if (double.IsNaN(size))
198.351 + {
198.352 + size = this.MarkerSize;
198.353 + }
198.354 +
198.355 + var screenPoint = this.XAxis.Transform(dp.X, dp.Y, this.YAxis);
198.356 +
198.357 + if (this.ColorAxis != null)
198.358 + {
198.359 + if (!double.IsNaN(value))
198.360 + {
198.361 + int group = this.ColorAxis.GetPaletteIndex(value);
198.362 + if (!groupPoints.ContainsKey(group))
198.363 + {
198.364 + groupPoints.Add(group, new List<ScreenPoint>());
198.365 + groupSizes.Add(group, new List<double>());
198.366 + }
198.367 +
198.368 + groupPoints[group].Add(screenPoint);
198.369 + groupSizes[group].Add(size);
198.370 + }
198.371 + }
198.372 + else
198.373 + {
198.374 + // ReSharper disable PossibleNullReferenceException
198.375 + allPoints[i] = screenPoint;
198.376 + markerSizes[i] = size;
198.377 + // ReSharper restore PossibleNullReferenceException
198.378 + }
198.379 + }
198.380 +
198.381 + var binOffset = this.XAxis.Transform(this.MinX, this.MaxY, this.YAxis);
198.382 +
198.383 + // Draw the markers
198.384 + if (this.ColorAxis != null)
198.385 + {
198.386 + var markerIsStrokedOnly = this.MarkerType == MarkerType.Plus || this.MarkerType == MarkerType.Star
198.387 + || this.MarkerType == MarkerType.Cross;
198.388 + foreach (var group in groupPoints)
198.389 + {
198.390 + var color = this.ColorAxis.GetColor(group.Key);
198.391 + rc.DrawMarkers(
198.392 + group.Value,
198.393 + clippingRect,
198.394 + this.MarkerType,
198.395 + this.MarkerOutline,
198.396 + groupSizes[group.Key],
198.397 + color,
198.398 + markerIsStrokedOnly ? color : this.MarkerStroke,
198.399 + this.MarkerStrokeThickness,
198.400 + this.BinSize,
198.401 + binOffset);
198.402 + }
198.403 + }
198.404 + else
198.405 + {
198.406 + rc.DrawMarkers(
198.407 + allPoints,
198.408 + clippingRect,
198.409 + this.MarkerType,
198.410 + this.MarkerOutline,
198.411 + markerSizes,
198.412 + this.ActualMarkerFillColor,
198.413 + this.MarkerStroke,
198.414 + this.MarkerStrokeThickness,
198.415 + this.BinSize,
198.416 + binOffset);
198.417 + }
198.418 + }
198.419 +
198.420 + /// <summary>
198.421 + /// Renders the legend symbol for the line series on the specified rendering context.
198.422 + /// </summary>
198.423 + /// <param name="rc">
198.424 + /// The rendering context.
198.425 + /// </param>
198.426 + /// <param name="legendBox">
198.427 + /// The bounding rectangle of the legend box.
198.428 + /// </param>
198.429 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
198.430 + {
198.431 + double xmid = (legendBox.Left + legendBox.Right) / 2;
198.432 + double ymid = (legendBox.Top + legendBox.Bottom) / 2;
198.433 +
198.434 + var midpt = new ScreenPoint(xmid, ymid);
198.435 + rc.DrawMarker(
198.436 + midpt,
198.437 + legendBox,
198.438 + this.MarkerType,
198.439 + this.MarkerOutline,
198.440 + this.MarkerSize,
198.441 + this.ActualMarkerFillColor,
198.442 + this.MarkerStroke,
198.443 + this.MarkerStrokeThickness);
198.444 + }
198.445 +
198.446 + /// <summary>
198.447 + /// Ensures that the axes of the series is defined.
198.448 + /// </summary>
198.449 + protected internal override void EnsureAxes()
198.450 + {
198.451 + base.EnsureAxes();
198.452 +
198.453 + this.ColorAxis = PlotModel.GetAxisOrDefault(this.ColorAxisKey, PlotModel.DefaultColorAxis) as ColorAxis;
198.454 + }
198.455 +
198.456 + /// <summary>
198.457 + /// Sets the default values.
198.458 + /// </summary>
198.459 + /// <param name="model">
198.460 + /// The model.
198.461 + /// </param>
198.462 + protected internal override void SetDefaultValues(PlotModel model)
198.463 + {
198.464 + if (this.MarkerFill == null)
198.465 + {
198.466 + this.defaultMarkerFillColor = model.GetDefaultColor();
198.467 + }
198.468 + }
198.469 +
198.470 + /// <summary>
198.471 + /// The update data.
198.472 + /// </summary>
198.473 + protected internal override void UpdateData()
198.474 + {
198.475 + if (this.ItemsSource == null)
198.476 + {
198.477 + return;
198.478 + }
198.479 +
198.480 + var points = this.Points;
198.481 + points.Clear();
198.482 +
198.483 + // Use the mapping to generate the points
198.484 + if (this.Mapping != null)
198.485 + {
198.486 + foreach (var item in this.ItemsSource)
198.487 + {
198.488 + points.Add(this.Mapping(item));
198.489 + }
198.490 +
198.491 + return;
198.492 + }
198.493 +
198.494 + // Get DataPoints from the items in ItemsSource
198.495 + // if they implement IScatterPointProvider
198.496 + // If DataFields are set, this is not used
198.497 + /*if (DataFieldX == null || DataFieldY == null)
198.498 + {
198.499 + foreach (var item in ItemsSource)
198.500 + {
198.501 + var idpp = item as IScatterPointProvider;
198.502 + if (idpp == null)
198.503 + {
198.504 + continue;
198.505 + }
198.506 +
198.507 + points.Add(idpp.GetScatterPoint());
198.508 + }
198.509 +
198.510 + return;
198.511 + }*/
198.512 +
198.513 + var dest = new List<IDataPoint>();
198.514 +
198.515 + // Using reflection to add points
198.516 + var filler = new ListFiller<ScatterPoint>();
198.517 + filler.Add(this.DataFieldX, (item, value) => item.X = Convert.ToDouble(value));
198.518 + filler.Add(this.DataFieldY, (item, value) => item.Y = Convert.ToDouble(value));
198.519 + filler.Add(this.DataFieldSize, (item, value) => item.Size = Convert.ToDouble(value));
198.520 + filler.Add(this.DataFieldValue, (item, value) => item.Value = Convert.ToDouble(value));
198.521 + filler.Add(this.DataFieldTag, (item, value) => item.Tag = value);
198.522 + filler.Fill(dest, this.ItemsSource);
198.523 +
198.524 + this.Points = dest;
198.525 + }
198.526 +
198.527 + /// <summary>
198.528 + /// Updates the max/min from the data points.
198.529 + /// </summary>
198.530 + protected internal override void UpdateMaxMin()
198.531 + {
198.532 + base.UpdateMaxMin();
198.533 + this.InternalUpdateMaxMinValue(this.Points);
198.534 + }
198.535 +
198.536 + /// <summary>
198.537 + /// Adds scatter points specified by a items source and data fields.
198.538 + /// </summary>
198.539 + /// <param name="dest">
198.540 + /// The destination collection.
198.541 + /// </param>
198.542 + /// <param name="itemsSource">
198.543 + /// The items source.
198.544 + /// </param>
198.545 + /// <param name="dataFieldX">
198.546 + /// The data field x.
198.547 + /// </param>
198.548 + /// <param name="dataFieldY">
198.549 + /// The data field y.
198.550 + /// </param>
198.551 + /// <param name="dataFieldSize">
198.552 + /// The data field size.
198.553 + /// </param>
198.554 + /// <param name="dataFieldValue">
198.555 + /// The data field value.
198.556 + /// </param>
198.557 + /// <param name="dataFieldTag">
198.558 + /// The data field tag.
198.559 + /// </param>
198.560 + protected void AddScatterPoints(
198.561 + IList<ScatterPoint> dest,
198.562 + IEnumerable itemsSource,
198.563 + string dataFieldX,
198.564 + string dataFieldY,
198.565 + string dataFieldSize,
198.566 + string dataFieldValue,
198.567 + string dataFieldTag)
198.568 + {
198.569 + var filler = new ListFiller<ScatterPoint>();
198.570 + filler.Add(dataFieldX, (item, value) => item.X = Convert.ToDouble(value));
198.571 + filler.Add(dataFieldY, (item, value) => item.Y = Convert.ToDouble(value));
198.572 + filler.Add(dataFieldSize, (item, value) => item.Size = Convert.ToDouble(value));
198.573 + filler.Add(dataFieldValue, (item, value) => item.Value = Convert.ToDouble(value));
198.574 + filler.Add(dataFieldTag, (item, value) => item.Tag = value);
198.575 + filler.FillT(dest, itemsSource);
198.576 + }
198.577 +
198.578 + /// <summary>
198.579 + /// Updates the Max/Min limits from the values in the specified point list.
198.580 + /// </summary>
198.581 + /// <param name="pts">
198.582 + /// The points.
198.583 + /// </param>
198.584 + protected void InternalUpdateMaxMinValue(IList<IDataPoint> pts)
198.585 + {
198.586 + if (pts == null || pts.Count == 0)
198.587 + {
198.588 + return;
198.589 + }
198.590 +
198.591 + double minvalue = double.NaN;
198.592 + double maxvalue = double.NaN;
198.593 +
198.594 + foreach (var pt in pts)
198.595 + {
198.596 + if (!(pt is ScatterPoint))
198.597 + {
198.598 + continue;
198.599 + }
198.600 +
198.601 + double value = ((ScatterPoint)pt).value;
198.602 +
198.603 + if (value < minvalue || double.IsNaN(minvalue))
198.604 + {
198.605 + minvalue = value;
198.606 + }
198.607 +
198.608 + if (value > maxvalue || double.IsNaN(maxvalue))
198.609 + {
198.610 + maxvalue = value;
198.611 + }
198.612 + }
198.613 +
198.614 + this.MinValue = minvalue;
198.615 + this.MaxValue = maxvalue;
198.616 +
198.617 + if (this.ColorAxis != null)
198.618 + {
198.619 + this.ColorAxis.Include(this.MinValue);
198.620 + this.ColorAxis.Include(this.MaxValue);
198.621 + }
198.622 + }
198.623 + }
198.624 +}
198.625 \ No newline at end of file
199.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
199.2 +++ b/External/OxyPlot/OxyPlot/Series/Series.cs Sat Jun 08 16:53:22 2013 +0000
199.3 @@ -0,0 +1,204 @@
199.4 +// --------------------------------------------------------------------------------------------------------------------
199.5 +// <copyright file="Series.cs" company="OxyPlot">
199.6 +// The MIT License (MIT)
199.7 +//
199.8 +// Copyright (c) 2012 Oystein Bjorke
199.9 +//
199.10 +// Permission is hereby granted, free of charge, to any person obtaining a
199.11 +// copy of this software and associated documentation files (the
199.12 +// "Software"), to deal in the Software without restriction, including
199.13 +// without limitation the rights to use, copy, modify, merge, publish,
199.14 +// distribute, sublicense, and/or sell copies of the Software, and to
199.15 +// permit persons to whom the Software is furnished to do so, subject to
199.16 +// the following conditions:
199.17 +//
199.18 +// The above copyright notice and this permission notice shall be included
199.19 +// in all copies or substantial portions of the Software.
199.20 +//
199.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
199.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
199.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
199.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
199.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
199.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
199.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
199.28 +// </copyright>
199.29 +// <summary>
199.30 +// Abstract base class for all series.
199.31 +// </summary>
199.32 +// --------------------------------------------------------------------------------------------------------------------
199.33 +namespace OxyPlot.Series
199.34 +{
199.35 + using System.Globalization;
199.36 +
199.37 + using OxyPlot.Axes;
199.38 +
199.39 + /// <summary>
199.40 + /// Provides an abstract base class for plot series.
199.41 + /// </summary>
199.42 + /// <remarks>
199.43 + /// This class contains internal methods that should be called only from the PlotModel.
199.44 + /// </remarks>
199.45 + public abstract class Series : UIPlotElement, ITrackableSeries
199.46 + {
199.47 + /// <summary>
199.48 + /// Initializes a new instance of the <see cref="Series" /> class.
199.49 + /// </summary>
199.50 + protected Series()
199.51 + {
199.52 + this.IsVisible = true;
199.53 + }
199.54 +
199.55 + /// <summary>
199.56 + /// Gets the actual culture.
199.57 + /// </summary>
199.58 + /// <remarks>
199.59 + /// The culture is defined in the parent PlotModel.
199.60 + /// </remarks>
199.61 + public CultureInfo ActualCulture
199.62 + {
199.63 + get
199.64 + {
199.65 + return this.PlotModel != null ? this.PlotModel.ActualCulture : CultureInfo.CurrentCulture;
199.66 + }
199.67 + }
199.68 +
199.69 + /// <summary>
199.70 + /// Gets or sets the background color of the series. The background area is defined by the x and y axes.
199.71 + /// </summary>
199.72 + /// <value> The background color. </value>
199.73 + public OxyColor Background { get; set; }
199.74 +
199.75 + /// <summary>
199.76 + /// Gets or sets a value indicating whether this series is visible.
199.77 + /// </summary>
199.78 + public bool IsVisible { get; set; }
199.79 +
199.80 + /// <summary>
199.81 + /// Gets or sets the title of the Series.
199.82 + /// </summary>
199.83 + /// <value> The title. </value>
199.84 + public string Title { get; set; }
199.85 +
199.86 + /// <summary>
199.87 + /// Gets or sets a format string used for the tracker.
199.88 + /// </summary>
199.89 + public string TrackerFormatString { get; set; }
199.90 +
199.91 + /// <summary>
199.92 + /// Gets or sets the key for the tracker to use on this series.
199.93 + /// </summary>
199.94 + public string TrackerKey { get; set; }
199.95 +
199.96 + /// <summary>
199.97 + /// Gets the point on the series that is nearest the specified point.
199.98 + /// </summary>
199.99 + /// <param name="point">The point.</param>
199.100 + /// <param name="interpolate">Interpolate the series if this flag is set to <c>true</c>.</param>
199.101 + /// <returns>
199.102 + /// A TrackerHitResult for the current hit.
199.103 + /// </returns>
199.104 + public abstract TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate);
199.105 +
199.106 + /// <summary>
199.107 + /// Renders the series on the specified render context.
199.108 + /// </summary>
199.109 + /// <param name="rc">
199.110 + /// The rendering context.
199.111 + /// </param>
199.112 + /// <param name="model">
199.113 + /// The model.
199.114 + /// </param>
199.115 + public abstract void Render(IRenderContext rc, PlotModel model);
199.116 +
199.117 + /// <summary>
199.118 + /// Renders the legend symbol on the specified render context.
199.119 + /// </summary>
199.120 + /// <param name="rc">
199.121 + /// The rendering context.
199.122 + /// </param>
199.123 + /// <param name="legendBox">
199.124 + /// The legend rectangle.
199.125 + /// </param>
199.126 + public abstract void RenderLegend(IRenderContext rc, OxyRect legendBox);
199.127 +
199.128 + /// <summary>
199.129 + /// Tests if the plot element is hit by the specified point.
199.130 + /// </summary>
199.131 + /// <param name="point">The point.</param>
199.132 + /// <param name="tolerance">The tolerance.</param>
199.133 + /// <returns>
199.134 + /// A hit test result.
199.135 + /// </returns>
199.136 + protected internal override HitTestResult HitTest(ScreenPoint point, double tolerance)
199.137 + {
199.138 + var thr = this.GetNearestPoint(point, true) ?? this.GetNearestPoint(point, false);
199.139 +
199.140 + if (thr != null)
199.141 + {
199.142 + double distance = thr.Position.DistanceTo(point);
199.143 + if (distance > tolerance)
199.144 + {
199.145 + return null;
199.146 + }
199.147 +
199.148 + return new HitTestResult(thr.Position, thr.Item, thr.Index);
199.149 + }
199.150 +
199.151 + return null;
199.152 + }
199.153 +
199.154 + /// <summary>
199.155 + /// Check if this data series requires X/Y axes. (e.g. Pie series do not require axes)
199.156 + /// </summary>
199.157 + /// <returns>
199.158 + /// True if no axes are required.
199.159 + /// </returns>
199.160 + protected internal abstract bool AreAxesRequired();
199.161 +
199.162 + /// <summary>
199.163 + /// Ensures that the axes of the series is defined.
199.164 + /// </summary>
199.165 + protected internal abstract void EnsureAxes();
199.166 +
199.167 + /// <summary>
199.168 + /// Check if the data series is using the specified axis.
199.169 + /// </summary>
199.170 + /// <param name="axis">
199.171 + /// An axis which should be checked if used
199.172 + /// </param>
199.173 + /// <returns>
199.174 + /// True if the axis is in use.
199.175 + /// </returns>
199.176 + protected internal abstract bool IsUsing(Axis axis);
199.177 +
199.178 + /// <summary>
199.179 + /// Sets default values (colors, line style etc) from the plot model.
199.180 + /// </summary>
199.181 + /// <param name="model">
199.182 + /// A plot model.
199.183 + /// </param>
199.184 + protected internal abstract void SetDefaultValues(PlotModel model);
199.185 +
199.186 + /// <summary>
199.187 + /// Updates the axis maximum and minimum values.
199.188 + /// </summary>
199.189 + protected internal abstract void UpdateAxisMaxMin();
199.190 +
199.191 + /// <summary>
199.192 + /// Updates the data.
199.193 + /// </summary>
199.194 + protected internal abstract void UpdateData();
199.195 +
199.196 + /// <summary>
199.197 + /// Updates the valid data.
199.198 + /// </summary>
199.199 + protected internal abstract void UpdateValidData();
199.200 +
199.201 + /// <summary>
199.202 + /// Updates the maximum and minimum of the series.
199.203 + /// </summary>
199.204 + protected internal abstract void UpdateMaxMin();
199.205 +
199.206 + }
199.207 +}
199.208 \ No newline at end of file
200.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
200.2 +++ b/External/OxyPlot/OxyPlot/Series/StairStepSeries.cs Sat Jun 08 16:53:22 2013 +0000
200.3 @@ -0,0 +1,291 @@
200.4 +// --------------------------------------------------------------------------------------------------------------------
200.5 +// <copyright file="StairStepSeries.cs" company="OxyPlot">
200.6 +// The MIT License (MIT)
200.7 +//
200.8 +// Copyright (c) 2012 Oystein Bjorke
200.9 +//
200.10 +// Permission is hereby granted, free of charge, to any person obtaining a
200.11 +// copy of this software and associated documentation files (the
200.12 +// "Software"), to deal in the Software without restriction, including
200.13 +// without limitation the rights to use, copy, modify, merge, publish,
200.14 +// distribute, sublicense, and/or sell copies of the Software, and to
200.15 +// permit persons to whom the Software is furnished to do so, subject to
200.16 +// the following conditions:
200.17 +//
200.18 +// The above copyright notice and this permission notice shall be included
200.19 +// in all copies or substantial portions of the Software.
200.20 +//
200.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
200.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
200.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
200.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
200.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
200.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
200.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
200.28 +// </copyright>
200.29 +// <summary>
200.30 +// Represents a series for stair step graphs.
200.31 +// </summary>
200.32 +// --------------------------------------------------------------------------------------------------------------------
200.33 +namespace OxyPlot.Series
200.34 +{
200.35 + using System;
200.36 + using System.Collections.Generic;
200.37 +
200.38 + /// <summary>
200.39 + /// Represents a series for stair step graphs.
200.40 + /// </summary>
200.41 + public class StairStepSeries : LineSeries
200.42 + {
200.43 + /// <summary>
200.44 + /// Initializes a new instance of the <see cref = "StairStepSeries" /> class.
200.45 + /// </summary>
200.46 + public StairStepSeries()
200.47 + {
200.48 + this.VerticalStrokeThickness = double.NaN;
200.49 + this.VerticalLineStyle = this.LineStyle;
200.50 + }
200.51 +
200.52 + /// <summary>
200.53 + /// Initializes a new instance of the <see cref="StairStepSeries"/> class.
200.54 + /// </summary>
200.55 + /// <param name="title">
200.56 + /// The title.
200.57 + /// </param>
200.58 + public StairStepSeries(string title)
200.59 + : base(title)
200.60 + {
200.61 + this.VerticalStrokeThickness = double.NaN;
200.62 + this.VerticalLineStyle = this.LineStyle;
200.63 + this.Title = title;
200.64 + }
200.65 +
200.66 + /// <summary>
200.67 + /// Initializes a new instance of the <see cref="StairStepSeries"/> class.
200.68 + /// </summary>
200.69 + /// <param name="color">
200.70 + /// The color.
200.71 + /// </param>
200.72 + /// <param name="strokeThickness">
200.73 + /// The stroke thickness.
200.74 + /// </param>
200.75 + /// <param name="title">
200.76 + /// The title.
200.77 + /// </param>
200.78 + public StairStepSeries(OxyColor color, double strokeThickness = 1, string title = null)
200.79 + : base(color, strokeThickness, title)
200.80 + {
200.81 + this.VerticalStrokeThickness = double.NaN;
200.82 + this.VerticalLineStyle = this.LineStyle;
200.83 + }
200.84 +
200.85 + /// <summary>
200.86 + /// Gets or sets the stroke thickness of the vertical line segments.
200.87 + /// </summary>
200.88 + /// <remarks>
200.89 + /// Set the value to NaN to use the StrokeThickness property for both horizontal and vertical segments.
200.90 + /// Using the VerticalStrokeThickness property will have a small performance hit.
200.91 + /// </remarks>
200.92 + /// <value>The vertical stroke thickness.</value>
200.93 + public double VerticalStrokeThickness { get; set; }
200.94 +
200.95 + /// <summary>
200.96 + /// Gets or sets the line style of the vertical line segments.
200.97 + /// </summary>
200.98 + /// <value>The vertical line style.</value>
200.99 + public LineStyle VerticalLineStyle { get; set; }
200.100 +
200.101 + /// <summary>
200.102 + /// Gets the nearest point.
200.103 + /// </summary>
200.104 + /// <param name="point">
200.105 + /// The point.
200.106 + /// </param>
200.107 + /// <param name="interpolate">
200.108 + /// interpolate if set to <c>true</c> .
200.109 + /// </param>
200.110 + /// <returns>
200.111 + /// A TrackerHitResult for the current hit.
200.112 + /// </returns>
200.113 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
200.114 + {
200.115 + if (this.XAxis == null || this.YAxis == null)
200.116 + {
200.117 + return null;
200.118 + }
200.119 +
200.120 + TrackerHitResult result = null;
200.121 +
200.122 + // http://paulbourke.net/geometry/pointlineplane/
200.123 + double minimumDistance = double.MaxValue;
200.124 +
200.125 + for (int i = 0; i + 1 < this.Points.Count; i++)
200.126 + {
200.127 + var p1 = this.Points[i];
200.128 + var p2 = this.Points[i + 1];
200.129 + var sp1 = this.Transform(p1.X, p1.Y);
200.130 + var sp2 = this.Transform(p2.X, p1.Y);
200.131 +
200.132 + double spdx = sp2.x - sp1.x;
200.133 + double spdy = sp2.y - sp1.y;
200.134 + double u1 = ((point.x - sp1.x) * spdx) + ((point.y - sp1.y) * spdy);
200.135 + double u2 = (spdx * spdx) + (spdy * spdy);
200.136 + double ds = (spdx * spdx) + (spdy * spdy);
200.137 +
200.138 + if (ds < 4)
200.139 + {
200.140 + // if the points are very close, we can get numerical problems, just use the first point...
200.141 + u1 = 0;
200.142 + u2 = 1;
200.143 + }
200.144 +
200.145 + if (Math.Abs(u2) < double.Epsilon)
200.146 + {
200.147 + continue; // P1 && P2 coincident
200.148 + }
200.149 +
200.150 + double u = u1 / u2;
200.151 + if (u < 0 || u > 1)
200.152 + {
200.153 + continue; // outside line
200.154 + }
200.155 +
200.156 + double sx = sp1.x + (u * spdx);
200.157 + double sy = sp1.y + (u * spdy);
200.158 +
200.159 + double dx = point.x - sx;
200.160 + double dy = point.y - sy;
200.161 + double distance = (dx * dx) + (dy * dy);
200.162 +
200.163 + if (distance < minimumDistance)
200.164 + {
200.165 + double px = p1.X + (u * (p2.X - p1.X));
200.166 + double py = p1.Y;
200.167 + result = new TrackerHitResult(
200.168 + this, new DataPoint(px, py), new ScreenPoint(sx, sy), this.GetItem(i), i);
200.169 + minimumDistance = distance;
200.170 + }
200.171 + }
200.172 +
200.173 + return result;
200.174 + }
200.175 +
200.176 + /// <summary>
200.177 + /// Renders the LineSeries on the specified rendering context.
200.178 + /// </summary>
200.179 + /// <param name="rc">
200.180 + /// The rendering context.
200.181 + /// </param>
200.182 + /// <param name="model">
200.183 + /// The owner plot model.
200.184 + /// </param>
200.185 + public override void Render(IRenderContext rc, PlotModel model)
200.186 + {
200.187 + if (this.Points.Count == 0)
200.188 + {
200.189 + return;
200.190 + }
200.191 +
200.192 + this.VerifyAxes();
200.193 +
200.194 + var clippingRect = this.GetClippingRect();
200.195 +
200.196 + Action<IList<ScreenPoint>, IList<ScreenPoint>> renderPoints = (lpts, mpts) =>
200.197 + {
200.198 + var lineStyle = this.ActualLineStyle;
200.199 +
200.200 + // clip the line segments with the clipping rectangle
200.201 + if (this.StrokeThickness > 0 && lineStyle != LineStyle.None)
200.202 + {
200.203 + var verticalStrokeThickness = double.IsNaN(this.VerticalStrokeThickness)
200.204 + ? this.StrokeThickness
200.205 + : this.VerticalStrokeThickness;
200.206 + if (!verticalStrokeThickness.Equals(this.StrokeThickness) || this.VerticalLineStyle != lineStyle)
200.207 + {
200.208 + var hlpts = new List<ScreenPoint>();
200.209 + var vlpts = new List<ScreenPoint>();
200.210 + for (int i = 0; i + 2 < lpts.Count; i += 2)
200.211 + {
200.212 + hlpts.Add(lpts[i]);
200.213 + hlpts.Add(lpts[i + 1]);
200.214 + vlpts.Add(lpts[i + 1]);
200.215 + vlpts.Add(lpts[i + 2]);
200.216 + }
200.217 +
200.218 + rc.DrawClippedLineSegments(
200.219 + hlpts,
200.220 + clippingRect,
200.221 + this.GetSelectableColor(this.ActualColor),
200.222 + this.StrokeThickness,
200.223 + lineStyle,
200.224 + this.LineJoin,
200.225 + false);
200.226 + rc.DrawClippedLineSegments(
200.227 + vlpts,
200.228 + clippingRect,
200.229 + this.GetSelectableColor(this.ActualColor),
200.230 + verticalStrokeThickness,
200.231 + this.VerticalLineStyle,
200.232 + this.LineJoin,
200.233 + false);
200.234 + }
200.235 + else
200.236 + {
200.237 + rc.DrawClippedLine(
200.238 + lpts,
200.239 + clippingRect,
200.240 + 0,
200.241 + this.GetSelectableColor(this.ActualColor),
200.242 + this.StrokeThickness,
200.243 + lineStyle,
200.244 + this.LineJoin,
200.245 + false);
200.246 + }
200.247 + }
200.248 +
200.249 + if (this.MarkerType != MarkerType.None)
200.250 + {
200.251 + rc.DrawMarkers(
200.252 + mpts,
200.253 + clippingRect,
200.254 + this.MarkerType,
200.255 + this.MarkerOutline,
200.256 + new[] { this.MarkerSize },
200.257 + this.MarkerFill,
200.258 + this.MarkerStroke,
200.259 + this.MarkerStrokeThickness);
200.260 + }
200.261 + };
200.262 +
200.263 + // Transform all points to screen coordinates
200.264 + // Render the line when invalid points occur
200.265 + var linePoints = new List<ScreenPoint>();
200.266 + var markerPoints = new List<ScreenPoint>();
200.267 + double previousY = double.NaN;
200.268 + foreach (var point in this.Points)
200.269 + {
200.270 + if (!this.IsValidPoint(point, this.XAxis, this.YAxis))
200.271 + {
200.272 + renderPoints(linePoints, markerPoints);
200.273 + linePoints.Clear();
200.274 + markerPoints.Clear();
200.275 + previousY = double.NaN;
200.276 + continue;
200.277 + }
200.278 +
200.279 + ScreenPoint transformedPoint = this.Transform(point);
200.280 + if (!double.IsNaN(previousY))
200.281 + {
200.282 + // Horizontal line from the previous point to the current x-coordinate
200.283 + linePoints.Add(new ScreenPoint(transformedPoint.X, previousY));
200.284 + }
200.285 +
200.286 + linePoints.Add(transformedPoint);
200.287 + markerPoints.Add(transformedPoint);
200.288 + previousY = transformedPoint.Y;
200.289 + }
200.290 +
200.291 + renderPoints(linePoints, markerPoints);
200.292 + }
200.293 + }
200.294 +}
200.295 \ No newline at end of file
201.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
201.2 +++ b/External/OxyPlot/OxyPlot/Series/StemSeries.cs Sat Jun 08 16:53:22 2013 +0000
201.3 @@ -0,0 +1,212 @@
201.4 +// --------------------------------------------------------------------------------------------------------------------
201.5 +// <copyright file="StemSeries.cs" company="OxyPlot">
201.6 +// The MIT License (MIT)
201.7 +//
201.8 +// Copyright (c) 2012 Oystein Bjorke
201.9 +//
201.10 +// Permission is hereby granted, free of charge, to any person obtaining a
201.11 +// copy of this software and associated documentation files (the
201.12 +// "Software"), to deal in the Software without restriction, including
201.13 +// without limitation the rights to use, copy, modify, merge, publish,
201.14 +// distribute, sublicense, and/or sell copies of the Software, and to
201.15 +// permit persons to whom the Software is furnished to do so, subject to
201.16 +// the following conditions:
201.17 +//
201.18 +// The above copyright notice and this permission notice shall be included
201.19 +// in all copies or substantial portions of the Software.
201.20 +//
201.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
201.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
201.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
201.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
201.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
201.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
201.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
201.28 +// </copyright>
201.29 +// <summary>
201.30 +// Represents a series that plots discrete data in a stem plot.
201.31 +// </summary>
201.32 +// --------------------------------------------------------------------------------------------------------------------
201.33 +namespace OxyPlot.Series
201.34 +{
201.35 + using System.Collections.Generic;
201.36 +
201.37 + /// <summary>
201.38 + /// Represents a series that plots discrete data in a stem plot.
201.39 + /// </summary>
201.40 + /// <remarks>
201.41 + /// See <a href="http://en.wikipedia.org/wiki/Stemplot">Stem plot</a> and
201.42 + /// <a href="http://www.mathworks.com/help/techdoc/ref/stem.html">stem</a>.
201.43 + /// </remarks>
201.44 + public class StemSeries : LineSeries
201.45 + {
201.46 + /// <summary>
201.47 + /// Initializes a new instance of the <see cref = "StemSeries" /> class.
201.48 + /// </summary>
201.49 + public StemSeries()
201.50 + {
201.51 + this.Base = 0;
201.52 + }
201.53 +
201.54 + /// <summary>
201.55 + /// Initializes a new instance of the <see cref="StemSeries"/> class.
201.56 + /// </summary>
201.57 + /// <param name="title">
201.58 + /// The title.
201.59 + /// </param>
201.60 + public StemSeries(string title)
201.61 + : base(title)
201.62 + {
201.63 + this.Title = title;
201.64 + }
201.65 +
201.66 + /// <summary>
201.67 + /// Initializes a new instance of the <see cref="StemSeries"/> class.
201.68 + /// </summary>
201.69 + /// <param name="color">
201.70 + /// The color of the line stroke.
201.71 + /// </param>
201.72 + /// <param name="strokeThickness">
201.73 + /// The stroke thickness (optional).
201.74 + /// </param>
201.75 + /// <param name="title">
201.76 + /// The title (optional).
201.77 + /// </param>
201.78 + public StemSeries(OxyColor color, double strokeThickness = 1, string title = null)
201.79 + : base(color, strokeThickness, title)
201.80 + {
201.81 + }
201.82 +
201.83 + /// <summary>
201.84 + /// Gets or sets Base.
201.85 + /// </summary>
201.86 + public double Base { get; set; }
201.87 +
201.88 + /// <summary>
201.89 + /// Gets the point on the series that is nearest the specified point.
201.90 + /// </summary>
201.91 + /// <param name="point">
201.92 + /// The point.
201.93 + /// </param>
201.94 + /// <param name="interpolate">
201.95 + /// Interpolate the series if this flag is set to <c>true</c>.
201.96 + /// </param>
201.97 + /// <returns>
201.98 + /// A TrackerHitResult for the current hit.
201.99 + /// </returns>
201.100 + public override TrackerHitResult GetNearestPoint(ScreenPoint point, bool interpolate)
201.101 + {
201.102 + if (this.XAxis == null || this.YAxis == null)
201.103 + {
201.104 + return null;
201.105 + }
201.106 +
201.107 + if (interpolate)
201.108 + {
201.109 + return null;
201.110 + }
201.111 +
201.112 + TrackerHitResult result = null;
201.113 +
201.114 + // http://paulbourke.net/geometry/pointlineplane/
201.115 + double minimumDistance = double.MaxValue;
201.116 + var points = this.Points;
201.117 +
201.118 + for (int i = 0; i < points.Count; i++)
201.119 + {
201.120 + var p1 = points[i];
201.121 + var basePoint = new DataPoint(p1.X, this.Base);
201.122 + var sp1 = this.Transform(p1);
201.123 + var sp2 = this.Transform(basePoint);
201.124 + var u = ScreenPointHelper.FindPositionOnLine(point, sp1, sp2);
201.125 +
201.126 + if (double.IsNaN(u))
201.127 + {
201.128 + continue;
201.129 + }
201.130 +
201.131 + if (u < 0 || u > 1)
201.132 + {
201.133 + continue; // outside line
201.134 + }
201.135 +
201.136 + var sp = sp1 + ((sp2 - sp1) * u);
201.137 + double distance = (point - sp).LengthSquared;
201.138 +
201.139 + if (distance < minimumDistance)
201.140 + {
201.141 + result = new TrackerHitResult(
201.142 + this, new DataPoint(p1.X, p1.Y), new ScreenPoint(sp1.x, sp1.y), this.GetItem(i));
201.143 + minimumDistance = distance;
201.144 + }
201.145 + }
201.146 +
201.147 + return result;
201.148 + }
201.149 +
201.150 + /// <summary>
201.151 + /// Renders the LineSeries on the specified rendering context.
201.152 + /// </summary>
201.153 + /// <param name="rc">
201.154 + /// The rendering context.
201.155 + /// </param>
201.156 + /// <param name="model">
201.157 + /// The owner plot model.
201.158 + /// </param>
201.159 + public override void Render(IRenderContext rc, PlotModel model)
201.160 + {
201.161 + if (this.Points.Count == 0)
201.162 + {
201.163 + return;
201.164 + }
201.165 +
201.166 + this.VerifyAxes();
201.167 +
201.168 + double minDistSquared = this.MinimumSegmentLength * this.MinimumSegmentLength;
201.169 +
201.170 + var clippingRect = this.GetClippingRect();
201.171 +
201.172 + // Transform all points to screen coordinates
201.173 + // Render the line when invalid points occur
201.174 + var markerPoints = new List<ScreenPoint>();
201.175 + foreach (var point in this.Points)
201.176 + {
201.177 + if (!this.IsValidPoint(point, this.XAxis, this.YAxis))
201.178 + {
201.179 + continue;
201.180 + }
201.181 +
201.182 + var p0 = this.Transform(point.X, this.Base);
201.183 + var p1 = this.Transform(point.X, point.Y);
201.184 +
201.185 + if (this.StrokeThickness > 0 && this.ActualLineStyle != LineStyle.None)
201.186 + {
201.187 + rc.DrawClippedLine(
201.188 + new[] { p0, p1 },
201.189 + clippingRect,
201.190 + minDistSquared,
201.191 + this.GetSelectableColor(this.ActualColor),
201.192 + this.StrokeThickness,
201.193 + this.ActualLineStyle,
201.194 + this.LineJoin,
201.195 + false);
201.196 + }
201.197 +
201.198 + markerPoints.Add(p1);
201.199 + }
201.200 +
201.201 + if (this.MarkerType != MarkerType.None)
201.202 + {
201.203 + rc.DrawMarkers(
201.204 + markerPoints,
201.205 + clippingRect,
201.206 + this.MarkerType,
201.207 + this.MarkerOutline,
201.208 + new[] { this.MarkerSize },
201.209 + this.MarkerFill,
201.210 + this.MarkerStroke,
201.211 + this.MarkerStrokeThickness);
201.212 + }
201.213 + }
201.214 + }
201.215 +}
201.216 \ No newline at end of file
202.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
202.2 +++ b/External/OxyPlot/OxyPlot/Series/TwoColorLineSeries.cs Sat Jun 08 16:53:22 2013 +0000
202.3 @@ -0,0 +1,163 @@
202.4 +// --------------------------------------------------------------------------------------------------------------------
202.5 +// <copyright file="TwoColorLineSeries.cs" company="OxyPlot">
202.6 +// The MIT License (MIT)
202.7 +//
202.8 +// Copyright (c) 2012 Oystein Bjorke
202.9 +//
202.10 +// Permission is hereby granted, free of charge, to any person obtaining a
202.11 +// copy of this software and associated documentation files (the
202.12 +// "Software"), to deal in the Software without restriction, including
202.13 +// without limitation the rights to use, copy, modify, merge, publish,
202.14 +// distribute, sublicense, and/or sell copies of the Software, and to
202.15 +// permit persons to whom the Software is furnished to do so, subject to
202.16 +// the following conditions:
202.17 +//
202.18 +// The above copyright notice and this permission notice shall be included
202.19 +// in all copies or substantial portions of the Software.
202.20 +//
202.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
202.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
202.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
202.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
202.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
202.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
202.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
202.28 +// </copyright>
202.29 +// <summary>
202.30 +// Represents a two-color line series.
202.31 +// </summary>
202.32 +// --------------------------------------------------------------------------------------------------------------------
202.33 +namespace OxyPlot.Series
202.34 +{
202.35 + using System.Collections.Generic;
202.36 +
202.37 + /// <summary>
202.38 + /// Represents a two-color line series.
202.39 + /// </summary>
202.40 + public class TwoColorLineSeries : LineSeries
202.41 + {
202.42 + /// <summary>
202.43 + /// The default second color.
202.44 + /// </summary>
202.45 + private OxyColor defaultColor2;
202.46 +
202.47 + /// <summary>
202.48 + /// Initializes a new instance of the <see cref = "TwoColorLineSeries" /> class.
202.49 + /// </summary>
202.50 + public TwoColorLineSeries()
202.51 + {
202.52 + this.Limit = 0.0;
202.53 + this.Color2 = OxyColors.Blue;
202.54 + this.LineStyle2 = LineStyle.Solid;
202.55 + }
202.56 +
202.57 + /// <summary>
202.58 + /// Gets or sets the color for the part of the line that is below the limit.
202.59 + /// </summary>
202.60 + public OxyColor Color2 { get; set; }
202.61 +
202.62 + /// <summary>
202.63 + /// Gets the actual second color.
202.64 + /// </summary>
202.65 + /// <value>The actual color.</value>
202.66 + public OxyColor ActualColor2
202.67 + {
202.68 + get { return this.Color2 ?? this.defaultColor2; }
202.69 + }
202.70 +
202.71 + /// <summary>
202.72 + /// Gets or sets the limit.
202.73 + /// </summary>
202.74 + /// <remarks>
202.75 + /// The parts of the line that is below this limit will be rendered with Color2.
202.76 + /// The parts of the line that is above the limit will be rendered with Color.
202.77 + /// </remarks>
202.78 + public double Limit { get; set; }
202.79 +
202.80 + /// <summary>
202.81 + /// Gets or sets the line style for the part of the line that is below the limit.
202.82 + /// </summary>
202.83 + /// <value>The line style.</value>
202.84 + public LineStyle LineStyle2 { get; set; }
202.85 +
202.86 + /// <summary>
202.87 + /// Gets the actual line style for the part of the line that is below the limit.
202.88 + /// </summary>
202.89 + /// <value>The line style.</value>
202.90 + public LineStyle ActualLineStyle2
202.91 + {
202.92 + get
202.93 + {
202.94 + return this.LineStyle2 != LineStyle.Undefined ? this.LineStyle2 : LineStyle.Solid;
202.95 + }
202.96 + }
202.97 +
202.98 + /// <summary>
202.99 + /// The set default values.
202.100 + /// </summary>
202.101 + /// <param name="model">
202.102 + /// The model.
202.103 + /// </param>
202.104 + protected internal override void SetDefaultValues(PlotModel model)
202.105 + {
202.106 + if (this.Color2 == null)
202.107 + {
202.108 + this.LineStyle2 = model.GetDefaultLineStyle();
202.109 + this.defaultColor2 = model.GetDefaultColor();
202.110 + }
202.111 + }
202.112 +
202.113 + /// <summary>
202.114 + /// Renders the smoothed line.
202.115 + /// </summary>
202.116 + /// <param name="rc">
202.117 + /// The render context.
202.118 + /// </param>
202.119 + /// <param name="clippingRect">
202.120 + /// The clipping rect.
202.121 + /// </param>
202.122 + /// <param name="pointsToRender">
202.123 + /// The points.
202.124 + /// </param>
202.125 + protected override void RenderSmoothedLine(IRenderContext rc, OxyRect clippingRect, IList<ScreenPoint> pointsToRender)
202.126 + {
202.127 + double bottom = clippingRect.Bottom;
202.128 +
202.129 + // todo: this does not work when y axis is reversed
202.130 + double y = this.YAxis.Transform(this.Limit);
202.131 +
202.132 + if (y < clippingRect.Top)
202.133 + {
202.134 + y = clippingRect.Top;
202.135 + }
202.136 +
202.137 + if (y > clippingRect.Bottom)
202.138 + {
202.139 + y = clippingRect.Bottom;
202.140 + }
202.141 +
202.142 + clippingRect.Bottom = y;
202.143 + rc.DrawClippedLine(
202.144 + pointsToRender,
202.145 + clippingRect,
202.146 + this.MinimumSegmentLength * this.MinimumSegmentLength,
202.147 + this.GetSelectableColor(this.ActualColor),
202.148 + this.StrokeThickness,
202.149 + this.ActualLineStyle,
202.150 + this.LineJoin,
202.151 + false);
202.152 + clippingRect.Top = y;
202.153 + clippingRect.Height = bottom - y;
202.154 + rc.DrawClippedLine(
202.155 + pointsToRender,
202.156 + clippingRect,
202.157 + this.MinimumSegmentLength * this.MinimumSegmentLength,
202.158 + this.GetSelectableColor(this.ActualColor2),
202.159 + this.StrokeThickness,
202.160 + this.ActualLineStyle2,
202.161 + this.LineJoin,
202.162 + false);
202.163 + }
202.164 +
202.165 + }
202.166 +}
202.167 \ No newline at end of file
203.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
203.2 +++ b/External/OxyPlot/OxyPlot/Series/XYAxisSeries.cs Sat Jun 08 16:53:22 2013 +0000
203.3 @@ -0,0 +1,424 @@
203.4 +// --------------------------------------------------------------------------------------------------------------------
203.5 +// <copyright file="XYAxisSeries.cs" company="OxyPlot">
203.6 +// The MIT License (MIT)
203.7 +//
203.8 +// Copyright (c) 2012 Oystein Bjorke
203.9 +//
203.10 +// Permission is hereby granted, free of charge, to any person obtaining a
203.11 +// copy of this software and associated documentation files (the
203.12 +// "Software"), to deal in the Software without restriction, including
203.13 +// without limitation the rights to use, copy, modify, merge, publish,
203.14 +// distribute, sublicense, and/or sell copies of the Software, and to
203.15 +// permit persons to whom the Software is furnished to do so, subject to
203.16 +// the following conditions:
203.17 +//
203.18 +// The above copyright notice and this permission notice shall be included
203.19 +// in all copies or substantial portions of the Software.
203.20 +//
203.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
203.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
203.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
203.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
203.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
203.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
203.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
203.28 +// </copyright>
203.29 +// <summary>
203.30 +// Abstract base class for series that contains an X-axis and Y-axis.
203.31 +// </summary>
203.32 +// --------------------------------------------------------------------------------------------------------------------
203.33 +
203.34 +namespace OxyPlot.Series
203.35 +{
203.36 + using System;
203.37 + using System.Collections.Generic;
203.38 +
203.39 + using OxyPlot.Axes;
203.40 +
203.41 + /// <summary>
203.42 + /// Provides an abstract base class for series that are related to an X-axis and a Y-axis.
203.43 + /// </summary>
203.44 + public abstract class XYAxisSeries : ItemsSeries
203.45 + {
203.46 + /// <summary>
203.47 + /// Gets or sets the maximum x-coordinate of the dataset.
203.48 + /// </summary>
203.49 + /// <value> The maximum x-coordinate. </value>
203.50 + public double MaxX { get; protected set; }
203.51 +
203.52 + /// <summary>
203.53 + /// Gets or sets the maximum y-coordinate of the dataset.
203.54 + /// </summary>
203.55 + /// <value> The maximum y-coordinate. </value>
203.56 + public double MaxY { get; protected set; }
203.57 +
203.58 + /// <summary>
203.59 + /// Gets or sets the minimum x-coordinate of the dataset.
203.60 + /// </summary>
203.61 + /// <value> The minimum x-coordinate. </value>
203.62 + public double MinX { get; protected set; }
203.63 +
203.64 + /// <summary>
203.65 + /// Gets or sets the minimum y-coordinate of the dataset.
203.66 + /// </summary>
203.67 + /// <value> The minimum y-coordinate. </value>
203.68 + public double MinY { get; protected set; }
203.69 +
203.70 + /// <summary>
203.71 + /// Gets the x-axis.
203.72 + /// </summary>
203.73 + /// <value> The x-axis. </value>
203.74 + public Axis XAxis { get; private set; }
203.75 +
203.76 + /// <summary>
203.77 + /// Gets or sets the x-axis key.
203.78 + /// </summary>
203.79 + /// <value> The x-axis key. </value>
203.80 + public string XAxisKey { get; set; }
203.81 +
203.82 + /// <summary>
203.83 + /// Gets the y-axis.
203.84 + /// </summary>
203.85 + /// <value> The y-axis. </value>
203.86 + public Axis YAxis { get; private set; }
203.87 +
203.88 + /// <summary>
203.89 + /// Gets or sets the y-axis key.
203.90 + /// </summary>
203.91 + /// <value> The y-axis key. </value>
203.92 + public string YAxisKey { get; set; }
203.93 +
203.94 + /// <summary>
203.95 + /// Gets the rectangle the series uses on the screen (screen coordinates).
203.96 + /// </summary>
203.97 + /// <returns>
203.98 + /// The rectangle.
203.99 + /// </returns>
203.100 + public OxyRect GetScreenRectangle()
203.101 + {
203.102 + return this.GetClippingRect();
203.103 + }
203.104 +
203.105 + /// <summary>
203.106 + /// Renders the legend symbol on the specified rendering context.
203.107 + /// </summary>
203.108 + /// <param name="rc">
203.109 + /// The rendering context.
203.110 + /// </param>
203.111 + /// <param name="legendBox">
203.112 + /// The legend rectangle.
203.113 + /// </param>
203.114 + public override void RenderLegend(IRenderContext rc, OxyRect legendBox)
203.115 + {
203.116 + }
203.117 +
203.118 + /// <summary>
203.119 + /// Transforms from a screen point to a data point by the axes of this series.
203.120 + /// </summary>
203.121 + /// <param name="p">
203.122 + /// The screen point.
203.123 + /// </param>
203.124 + /// <returns>
203.125 + /// A data point.
203.126 + /// </returns>
203.127 + public DataPoint InverseTransform(ScreenPoint p)
203.128 + {
203.129 + return this.XAxis.InverseTransform(p.X, p.Y, this.YAxis);
203.130 + }
203.131 +
203.132 + /// <summary>
203.133 + /// Transforms the specified coordinates to a screen point by the axes of this series.
203.134 + /// </summary>
203.135 + /// <param name="x">
203.136 + /// The x coordinate.
203.137 + /// </param>
203.138 + /// <param name="y">
203.139 + /// The y coordinate.
203.140 + /// </param>
203.141 + /// <returns>
203.142 + /// A screen point.
203.143 + /// </returns>
203.144 + public ScreenPoint Transform(double x, double y)
203.145 + {
203.146 + return this.XAxis.Transform(x, y, this.YAxis);
203.147 + }
203.148 +
203.149 + /// <summary>
203.150 + /// Transforms the specified data point to a screen point by the axes of this series.
203.151 + /// </summary>
203.152 + /// <param name="p">
203.153 + /// The point.
203.154 + /// </param>
203.155 + /// <returns>
203.156 + /// A screen point.
203.157 + /// </returns>
203.158 + public ScreenPoint Transform(IDataPoint p)
203.159 + {
203.160 + return this.XAxis.Transform(p.X, p.Y, this.YAxis);
203.161 + }
203.162 +
203.163 + /// <summary>
203.164 + /// Check if this data series requires X/Y axes. (e.g. Pie series do not require axes)
203.165 + /// </summary>
203.166 + /// <returns>
203.167 + /// The are axes required.
203.168 + /// </returns>
203.169 + protected internal override bool AreAxesRequired()
203.170 + {
203.171 + return true;
203.172 + }
203.173 +
203.174 + /// <summary>
203.175 + /// Ensures that the axes of the series is defined.
203.176 + /// </summary>
203.177 + protected internal override void EnsureAxes()
203.178 + {
203.179 + this.XAxis = PlotModel.GetAxisOrDefault(this.XAxisKey, PlotModel.DefaultXAxis);
203.180 + this.YAxis = PlotModel.GetAxisOrDefault(this.YAxisKey, PlotModel.DefaultYAxis);
203.181 + }
203.182 +
203.183 + /// <summary>
203.184 + /// Check if the data series is using the specified axis.
203.185 + /// </summary>
203.186 + /// <param name="axis">
203.187 + /// An axis.
203.188 + /// </param>
203.189 + /// <returns>
203.190 + /// True if the axis is in use.
203.191 + /// </returns>
203.192 + protected internal override bool IsUsing(Axis axis)
203.193 + {
203.194 + return false;
203.195 + }
203.196 +
203.197 + /// <summary>
203.198 + /// Sets default values from the plot model.
203.199 + /// </summary>
203.200 + /// <param name="model">
203.201 + /// The plot model.
203.202 + /// </param>
203.203 + protected internal override void SetDefaultValues(PlotModel model)
203.204 + {
203.205 + }
203.206 +
203.207 + /// <summary>
203.208 + /// Updates the axes to include the max and min of this series.
203.209 + /// </summary>
203.210 + protected internal override void UpdateAxisMaxMin()
203.211 + {
203.212 + this.XAxis.Include(this.MinX);
203.213 + this.XAxis.Include(this.MaxX);
203.214 + this.YAxis.Include(this.MinY);
203.215 + this.YAxis.Include(this.MaxY);
203.216 + }
203.217 +
203.218 + /// <summary>
203.219 + /// Updates the data.
203.220 + /// </summary>
203.221 + protected internal override void UpdateData()
203.222 + {
203.223 + }
203.224 +
203.225 + /// <summary>
203.226 + /// Updates the max/minimum values.
203.227 + /// </summary>
203.228 + protected internal override void UpdateMaxMin()
203.229 + {
203.230 + this.MinX = this.MinY = this.MaxX = this.MaxY = double.NaN;
203.231 + }
203.232 +
203.233 + /// <summary>
203.234 + /// Gets the clipping rectangle.
203.235 + /// </summary>
203.236 + /// <returns>
203.237 + /// The clipping rectangle.
203.238 + /// </returns>
203.239 + protected OxyRect GetClippingRect()
203.240 + {
203.241 + double minX = Math.Min(this.XAxis.ScreenMin.X, this.XAxis.ScreenMax.X);
203.242 + double minY = Math.Min(this.YAxis.ScreenMin.Y, this.YAxis.ScreenMax.Y);
203.243 + double maxX = Math.Max(this.XAxis.ScreenMin.X, this.XAxis.ScreenMax.X);
203.244 + double maxY = Math.Max(this.YAxis.ScreenMin.Y, this.YAxis.ScreenMax.Y);
203.245 +
203.246 + return new OxyRect(minX, minY, maxX - minX, maxY - minY);
203.247 + }
203.248 +
203.249 + /// <summary>
203.250 + /// Gets the point on the curve that is nearest the specified point.
203.251 + /// </summary>
203.252 + /// <param name="points">
203.253 + /// The point list.
203.254 + /// </param>
203.255 + /// <param name="point">
203.256 + /// The point.
203.257 + /// </param>
203.258 + /// <returns>
203.259 + /// A tracker hit result if a point was found.
203.260 + /// </returns>
203.261 + protected TrackerHitResult GetNearestInterpolatedPointInternal(IList<IDataPoint> points, ScreenPoint point)
203.262 + {
203.263 + if (this.XAxis == null || this.YAxis == null || points == null)
203.264 + {
203.265 + return null;
203.266 + }
203.267 +
203.268 + var spn = default(ScreenPoint);
203.269 + var dpn = default(DataPoint);
203.270 + double index = -1;
203.271 +
203.272 + double minimumDistance = double.MaxValue;
203.273 +
203.274 + for (int i = 0; i + 1 < points.Count; i++)
203.275 + {
203.276 + var p1 = points[i];
203.277 + var p2 = points[i + 1];
203.278 + if (!this.IsValidPoint(p1, this.XAxis, this.YAxis) || !this.IsValidPoint(p2, this.XAxis, this.YAxis))
203.279 + {
203.280 + continue;
203.281 + }
203.282 +
203.283 + var sp1 = this.Transform(p1);
203.284 + var sp2 = this.Transform(p2);
203.285 +
203.286 + // Find the nearest point on the line segment.
203.287 + var spl = ScreenPointHelper.FindPointOnLine(point, sp1, sp2);
203.288 +
203.289 + if (ScreenPoint.IsUndefined(spl))
203.290 + {
203.291 + // P1 && P2 coincident
203.292 + continue;
203.293 + }
203.294 +
203.295 + double l2 = (point - spl).LengthSquared;
203.296 +
203.297 + if (l2 < minimumDistance)
203.298 + {
203.299 + double u = (spl - sp1).Length / (sp2 - sp1).Length;
203.300 + dpn = new DataPoint(p1.X + (u * (p2.X - p1.X)), p1.Y + (u * (p2.Y - p1.Y)));
203.301 + spn = spl;
203.302 + minimumDistance = l2;
203.303 + index = i + u;
203.304 + }
203.305 + }
203.306 +
203.307 + if (minimumDistance < double.MaxValue)
203.308 + {
203.309 + object item = this.GetItem((int)index);
203.310 + return new TrackerHitResult(this, dpn, spn, item) { Index = index };
203.311 + }
203.312 +
203.313 + return null;
203.314 + }
203.315 +
203.316 + /// <summary>
203.317 + /// Gets the nearest point.
203.318 + /// </summary>
203.319 + /// <param name="points">
203.320 + /// The points (data coordinates).
203.321 + /// </param>
203.322 + /// <param name="point">
203.323 + /// The point (screen coordinates).
203.324 + /// </param>
203.325 + /// <returns>
203.326 + /// A <see cref="TrackerHitResult"/> if a point was found, null otherwise.
203.327 + /// </returns>
203.328 + protected TrackerHitResult GetNearestPointInternal(IEnumerable<IDataPoint> points, ScreenPoint point)
203.329 + {
203.330 + var spn = default(ScreenPoint);
203.331 + IDataPoint dpn = default(DataPoint);
203.332 + double index = -1;
203.333 +
203.334 + double minimumDistance = double.MaxValue;
203.335 + int i = 0;
203.336 + foreach (var p in points)
203.337 + {
203.338 + if (!this.IsValidPoint(p, this.XAxis, this.YAxis))
203.339 + {
203.340 + continue;
203.341 + }
203.342 +
203.343 + var sp = Axis.Transform(p, this.XAxis, this.YAxis);
203.344 + double d2 = (sp - point).LengthSquared;
203.345 +
203.346 + if (d2 < minimumDistance)
203.347 + {
203.348 + dpn = p;
203.349 + spn = sp;
203.350 + minimumDistance = d2;
203.351 + index = i;
203.352 + }
203.353 +
203.354 + i++;
203.355 + }
203.356 +
203.357 + if (minimumDistance < double.MaxValue)
203.358 + {
203.359 + object item = this.GetItem((int)index);
203.360 + return new TrackerHitResult(this, dpn, spn, item) { Index = index };
203.361 + }
203.362 +
203.363 + return null;
203.364 + }
203.365 +
203.366 + /// <summary>
203.367 + /// Determines whether the specified point is valid.
203.368 + /// </summary>
203.369 + /// <param name="pt">
203.370 + /// The point.
203.371 + /// </param>
203.372 + /// <param name="xaxis">
203.373 + /// The x axis.
203.374 + /// </param>
203.375 + /// <param name="yaxis">
203.376 + /// The y axis.
203.377 + /// </param>
203.378 + /// <returns>
203.379 + /// <c>true</c> if the point is valid; otherwise, <c>false</c> .
203.380 + /// </returns>
203.381 + protected virtual bool IsValidPoint(IDataPoint pt, Axis xaxis, Axis yaxis)
203.382 + {
203.383 + return !double.IsNaN(pt.X) && !double.IsInfinity(pt.X) && !double.IsNaN(pt.Y) && !double.IsInfinity(pt.Y)
203.384 + && (xaxis != null && xaxis.IsValidValue(pt.X)) && (yaxis != null && yaxis.IsValidValue(pt.Y));
203.385 + }
203.386 +
203.387 + /// <summary>
203.388 + /// Converts the value of the specified object to a double precision floating point number. DateTime objects are converted using DateTimeAxis.ToDouble and TimeSpan objects are converted using TimeSpanAxis.ToDouble
203.389 + /// </summary>
203.390 + /// <param name="value">
203.391 + /// The value.
203.392 + /// </param>
203.393 + /// <returns>
203.394 + /// The floating point number value.
203.395 + /// </returns>
203.396 + protected virtual double ToDouble(object value)
203.397 + {
203.398 + if (value is DateTime)
203.399 + {
203.400 + return DateTimeAxis.ToDouble((DateTime)value);
203.401 + }
203.402 +
203.403 + if (value is TimeSpan)
203.404 + {
203.405 + return ((TimeSpan)value).TotalSeconds;
203.406 + }
203.407 +
203.408 + return Convert.ToDouble(value);
203.409 + }
203.410 +
203.411 + /// <summary>
203.412 + /// Verifies that both axes are defined.
203.413 + /// </summary>
203.414 + protected void VerifyAxes()
203.415 + {
203.416 + if (this.XAxis == null)
203.417 + {
203.418 + throw new InvalidOperationException("XAxis not defined.");
203.419 + }
203.420 +
203.421 + if (this.YAxis == null)
203.422 + {
203.423 + throw new InvalidOperationException("YAxis not defined.");
203.424 + }
203.425 + }
203.426 + }
203.427 +}
203.428 \ No newline at end of file
204.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
204.2 +++ b/External/OxyPlot/OxyPlot/Svg/NativeMethods.cs Sat Jun 08 16:53:22 2013 +0000
204.3 @@ -0,0 +1,246 @@
204.4 +// --------------------------------------------------------------------------------------------------------------------
204.5 +// <copyright file="NativeMethods.cs" company="OxyPlot">
204.6 +// The MIT License (MIT)
204.7 +//
204.8 +// Copyright (c) 2012 Oystein Bjorke
204.9 +//
204.10 +// Permission is hereby granted, free of charge, to any person obtaining a
204.11 +// copy of this software and associated documentation files (the
204.12 +// "Software"), to deal in the Software without restriction, including
204.13 +// without limitation the rights to use, copy, modify, merge, publish,
204.14 +// distribute, sublicense, and/or sell copies of the Software, and to
204.15 +// permit persons to whom the Software is furnished to do so, subject to
204.16 +// the following conditions:
204.17 +//
204.18 +// The above copyright notice and this permission notice shall be included
204.19 +// in all copies or substantial portions of the Software.
204.20 +//
204.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
204.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
204.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
204.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
204.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
204.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
204.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
204.28 +// </copyright>
204.29 +// <summary>
204.30 +// Interface to GDI32 native methods.
204.31 +// </summary>
204.32 +// --------------------------------------------------------------------------------------------------------------------
204.33 +namespace OxyPlot
204.34 +{
204.35 + using System;
204.36 + using System.Runtime.InteropServices;
204.37 + using System.Text.RegularExpressions;
204.38 +
204.39 + /// <summary>
204.40 + /// Provides access to native graphics methods.
204.41 + /// </summary>
204.42 + public class NativeMethods
204.43 + {
204.44 + /// <summary>
204.45 + /// The delete dc.
204.46 + /// </summary>
204.47 + /// <param name="hdc">
204.48 + /// The hdc.
204.49 + /// </param>
204.50 + /// <returns>
204.51 + /// The delete dc.
204.52 + /// </returns>
204.53 + [DllImport("gdi32.dll")]
204.54 + internal static extern bool DeleteDC(IntPtr hdc);
204.55 +
204.56 + /// <summary>
204.57 + /// The delete object.
204.58 + /// </summary>
204.59 + /// <param name="hgdiobj">
204.60 + /// The hgdiobj.
204.61 + /// </param>
204.62 + /// <returns>
204.63 + /// The delete object.
204.64 + /// </returns>
204.65 + [DllImport("gdi32.dll")]
204.66 + internal static extern int DeleteObject(IntPtr hgdiobj);
204.67 +
204.68 + /// <summary>
204.69 + /// The get dc.
204.70 + /// </summary>
204.71 + /// <param name="hWnd">
204.72 + /// The h wnd.
204.73 + /// </param>
204.74 + /// <returns>
204.75 + /// </returns>
204.76 + [DllImport("user32.dll")]
204.77 + internal static extern IntPtr GetDC(IntPtr hWnd);
204.78 +
204.79 + /// <summary>
204.80 + /// The get text extent point 32.
204.81 + /// </summary>
204.82 + /// <param name="hdc">
204.83 + /// The hdc.
204.84 + /// </param>
204.85 + /// <param name="str">
204.86 + /// The str.
204.87 + /// </param>
204.88 + /// <param name="len">
204.89 + /// The len.
204.90 + /// </param>
204.91 + /// <param name="siz">
204.92 + /// The siz.
204.93 + /// </param>
204.94 + /// <returns>
204.95 + /// The get text extent point 32.
204.96 + /// </returns>
204.97 + [DllImport("gdi32.dll", CharSet = CharSet.Unicode)]
204.98 + internal static extern int GetTextExtentPoint32(IntPtr hdc, string str, int len, ref Size siz);
204.99 +
204.100 + /// <summary>
204.101 + /// The measure string.
204.102 + /// </summary>
204.103 + /// <param name="faceName">
204.104 + /// The font face name.
204.105 + /// </param>
204.106 + /// <param name="height">
204.107 + /// The height.
204.108 + /// </param>
204.109 + /// <param name="weight">
204.110 + /// The weight.
204.111 + /// </param>
204.112 + /// <param name="str">
204.113 + /// The string.
204.114 + /// </param>
204.115 + /// <returns>
204.116 + /// The size of the rendered string.
204.117 + /// </returns>
204.118 + public static OxySize MeasureString(string faceName, int height, int weight, string str)
204.119 + {
204.120 + var lines = Regex.Split(str, "\r\n");
204.121 + OxySize result = new OxySize(0, 0);
204.122 + foreach (var line in lines)
204.123 + {
204.124 + var hfont = CreateFont(height, 0, 0, 0, weight, 0, 0, 0, 0, 0, 0, 0, 0, faceName);
204.125 + var hdc = GetDC(IntPtr.Zero);
204.126 + var oldobj = SelectObject(hdc, hfont);
204.127 + var temp = GetTextExtent(hdc, line);
204.128 + SelectObject(hdc, oldobj);
204.129 + DeleteObject(hfont);
204.130 + DeleteDC(hdc);
204.131 + var lineSpacing = temp.Height / 3.0;
204.132 + result.Height += temp.Height + lineSpacing;
204.133 + result.Width = Math.Max(temp.Width * 1.28, result.Width);
204.134 + }
204.135 +
204.136 + return result;
204.137 + }
204.138 +
204.139 + /// <summary>
204.140 + /// The select object.
204.141 + /// </summary>
204.142 + /// <param name="hdc">
204.143 + /// The hdc.
204.144 + /// </param>
204.145 + /// <param name="hgdiObj">
204.146 + /// The hgdi obj.
204.147 + /// </param>
204.148 + /// <returns>
204.149 + /// </returns>
204.150 + [DllImport("gdi32.dll")]
204.151 + internal static extern IntPtr SelectObject(IntPtr hdc, IntPtr hgdiObj);
204.152 +
204.153 + /// <summary>
204.154 + /// The create font.
204.155 + /// </summary>
204.156 + /// <param name="nHeight">
204.157 + /// The n height.
204.158 + /// </param>
204.159 + /// <param name="nWidth">
204.160 + /// The n width.
204.161 + /// </param>
204.162 + /// <param name="nEscapement">
204.163 + /// The n escapement.
204.164 + /// </param>
204.165 + /// <param name="nOrientation">
204.166 + /// The n orientation.
204.167 + /// </param>
204.168 + /// <param name="fnWeight">
204.169 + /// The fn weight.
204.170 + /// </param>
204.171 + /// <param name="fdwItalic">
204.172 + /// The fdw italic.
204.173 + /// </param>
204.174 + /// <param name="fdwUnderline">
204.175 + /// The fdw underline.
204.176 + /// </param>
204.177 + /// <param name="fdwStrikeOut">
204.178 + /// The fdw strike out.
204.179 + /// </param>
204.180 + /// <param name="fdwCharSet">
204.181 + /// The fdw char set.
204.182 + /// </param>
204.183 + /// <param name="fdwOutputPrecision">
204.184 + /// The fdw output precision.
204.185 + /// </param>
204.186 + /// <param name="fdwClipPrecision">
204.187 + /// The fdw clip precision.
204.188 + /// </param>
204.189 + /// <param name="fdwQuality">
204.190 + /// The fdw quality.
204.191 + /// </param>
204.192 + /// <param name="fdwPitchAndFamily">
204.193 + /// The fdw pitch and family.
204.194 + /// </param>
204.195 + /// <param name="lpszFace">
204.196 + /// The lpsz face.
204.197 + /// </param>
204.198 + /// <returns>
204.199 + /// </returns>
204.200 + [DllImport("gdi32.dll", CharSet = CharSet.Unicode)]
204.201 + private static extern IntPtr CreateFont(
204.202 + int nHeight,
204.203 + int nWidth,
204.204 + int nEscapement,
204.205 + int nOrientation,
204.206 + int fnWeight,
204.207 + uint fdwItalic,
204.208 + uint fdwUnderline,
204.209 + uint fdwStrikeOut,
204.210 + uint fdwCharSet,
204.211 + uint fdwOutputPrecision,
204.212 + uint fdwClipPrecision,
204.213 + uint fdwQuality,
204.214 + uint fdwPitchAndFamily,
204.215 + string lpszFace);
204.216 +
204.217 + /// <summary>
204.218 + /// Gets the text extent.
204.219 + /// </summary>
204.220 + /// <param name="hdc">The HDC.</param>
204.221 + /// <param name="str">The STR.</param>
204.222 + /// <returns></returns>
204.223 + private static OxySize GetTextExtent(IntPtr hdc, string str)
204.224 + {
204.225 + Size sz = default(Size);
204.226 + sz.cx = 0;
204.227 + sz.cy = 0;
204.228 + GetTextExtentPoint32(hdc, str, str.Length, ref sz);
204.229 + return new OxySize(sz.cx, sz.cy);
204.230 + }
204.231 +
204.232 + /// <summary>
204.233 + /// The size.
204.234 + /// </summary>
204.235 + [StructLayout(LayoutKind.Sequential)]
204.236 + public struct Size
204.237 + {
204.238 + /// <summary>
204.239 + /// The cx.
204.240 + /// </summary>
204.241 + public int cx;
204.242 +
204.243 + /// <summary>
204.244 + /// The cy.
204.245 + /// </summary>
204.246 + public int cy;
204.247 + }
204.248 + }
204.249 +}
204.250 \ No newline at end of file
205.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
205.2 +++ b/External/OxyPlot/OxyPlot/Svg/SvgExporter.cs Sat Jun 08 16:53:22 2013 +0000
205.3 @@ -0,0 +1,85 @@
205.4 +// --------------------------------------------------------------------------------------------------------------------
205.5 +// <copyright file="SvgExporter.cs" company="OxyPlot">
205.6 +// The MIT License (MIT)
205.7 +//
205.8 +// Copyright (c) 2012 Oystein Bjorke
205.9 +//
205.10 +// Permission is hereby granted, free of charge, to any person obtaining a
205.11 +// copy of this software and associated documentation files (the
205.12 +// "Software"), to deal in the Software without restriction, including
205.13 +// without limitation the rights to use, copy, modify, merge, publish,
205.14 +// distribute, sublicense, and/or sell copies of the Software, and to
205.15 +// permit persons to whom the Software is furnished to do so, subject to
205.16 +// the following conditions:
205.17 +//
205.18 +// The above copyright notice and this permission notice shall be included
205.19 +// in all copies or substantial portions of the Software.
205.20 +//
205.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
205.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
205.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
205.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
205.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
205.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
205.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
205.28 +// </copyright>
205.29 +// <summary>
205.30 +// Exports plot models to svg.
205.31 +// </summary>
205.32 +// --------------------------------------------------------------------------------------------------------------------
205.33 +namespace OxyPlot
205.34 +{
205.35 + using System.IO;
205.36 +
205.37 + /// <summary>
205.38 + /// Exports plots to scalable vector graphics.
205.39 + /// </summary>
205.40 + public static class SvgExporter
205.41 + {
205.42 + /// <summary>
205.43 + /// Exports the specified model to a stream.
205.44 + /// </summary>
205.45 + /// <param name="model">The model.</param>
205.46 + /// <param name="stream">The output stream.</param>
205.47 + /// <param name="width">The width (points).</param>
205.48 + /// <param name="height">The height (points).</param>
205.49 + /// <param name="isDocument">if set to <c>true</c>, the xml headers will be included (?xml and !DOCTYPE).</param>
205.50 + /// <param name="textMeasurer">The text measurer.</param>
205.51 + public static void Export(PlotModel model, Stream stream, double width, double height, bool isDocument, IRenderContext textMeasurer)
205.52 + {
205.53 + using (var rc = new SvgRenderContext(stream, width, height, true, textMeasurer, model.Background))
205.54 + {
205.55 + model.Update();
205.56 + model.Render(rc, width, height);
205.57 + rc.Complete();
205.58 + rc.Flush();
205.59 + }
205.60 + }
205.61 +
205.62 + /// <summary>
205.63 + /// Exports to string.
205.64 + /// </summary>
205.65 + /// <param name="model">The model.</param>
205.66 + /// <param name="width">The width (points).</param>
205.67 + /// <param name="height">The height (points).</param>
205.68 + /// <param name="isDocument">if set to <c>true</c>, the xml headers will be included (?xml and !DOCTYPE).</param>
205.69 + /// <param name="textMeasurer">The text measurer.</param>
205.70 + /// <returns>
205.71 + /// The plot as a svg string.
205.72 + /// </returns>
205.73 + public static string ExportToString(PlotModel model, double width, double height, bool isDocument, IRenderContext textMeasurer)
205.74 + {
205.75 + string svg;
205.76 + using (var ms = new MemoryStream())
205.77 + {
205.78 + Export(model, ms, width, height, isDocument, textMeasurer);
205.79 + ms.Flush();
205.80 + ms.Position = 0;
205.81 + var sr = new StreamReader(ms);
205.82 + svg = sr.ReadToEnd();
205.83 + }
205.84 +
205.85 + return svg;
205.86 + }
205.87 + }
205.88 +}
205.89 \ No newline at end of file
206.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
206.2 +++ b/External/OxyPlot/OxyPlot/Svg/SvgRenderContext.cs Sat Jun 08 16:53:22 2013 +0000
206.3 @@ -0,0 +1,278 @@
206.4 +// --------------------------------------------------------------------------------------------------------------------
206.5 +// <copyright file="SvgRenderContext.cs" company="OxyPlot">
206.6 +// The MIT License (MIT)
206.7 +//
206.8 +// Copyright (c) 2012 Oystein Bjorke
206.9 +//
206.10 +// Permission is hereby granted, free of charge, to any person obtaining a
206.11 +// copy of this software and associated documentation files (the
206.12 +// "Software"), to deal in the Software without restriction, including
206.13 +// without limitation the rights to use, copy, modify, merge, publish,
206.14 +// distribute, sublicense, and/or sell copies of the Software, and to
206.15 +// permit persons to whom the Software is furnished to do so, subject to
206.16 +// the following conditions:
206.17 +//
206.18 +// The above copyright notice and this permission notice shall be included
206.19 +// in all copies or substantial portions of the Software.
206.20 +//
206.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
206.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
206.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
206.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
206.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
206.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
206.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
206.28 +// </copyright>
206.29 +// <summary>
206.30 +// The svg render context.
206.31 +// </summary>
206.32 +// --------------------------------------------------------------------------------------------------------------------
206.33 +namespace OxyPlot
206.34 +{
206.35 + using System;
206.36 + using System.Collections.Generic;
206.37 + using System.IO;
206.38 + using System.Text.RegularExpressions;
206.39 +
206.40 + /// <summary>
206.41 + /// Provides a render context for scalable vector graphics output.
206.42 + /// </summary>
206.43 + public class SvgRenderContext : RenderContextBase, IDisposable
206.44 + {
206.45 + /// <summary>
206.46 + /// The writer.
206.47 + /// </summary>
206.48 + private readonly SvgWriter w;
206.49 +
206.50 + /// <summary>
206.51 + /// The disposed flag.
206.52 + /// </summary>
206.53 + private bool disposed;
206.54 +
206.55 + /// <summary>
206.56 + /// Initializes a new instance of the <see cref="SvgRenderContext" /> class.
206.57 + /// </summary>
206.58 + /// <param name="s">The s.</param>
206.59 + /// <param name="width">The width.</param>
206.60 + /// <param name="height">The height.</param>
206.61 + /// <param name="isDocument">Create an SVG document if set to <c>true</c>.</param>
206.62 + /// <param name="textMeasurer">The text measurer.</param>
206.63 + /// <param name="background">The background.</param>
206.64 + public SvgRenderContext(Stream s, double width, double height, bool isDocument, IRenderContext textMeasurer, OxyColor background)
206.65 + {
206.66 + if (textMeasurer == null)
206.67 + {
206.68 + throw new ArgumentNullException("textMeasurer", "A text measuring render context must be provided.");
206.69 + }
206.70 +
206.71 + this.w = new SvgWriter(s, width, height, isDocument);
206.72 + this.TextMeasurer = textMeasurer;
206.73 + if (background != null)
206.74 + {
206.75 + this.w.WriteRectangle(0, 0, width, height, this.w.CreateStyle(background, null, 0));
206.76 + }
206.77 + }
206.78 +
206.79 + /// <summary>
206.80 + /// Gets or sets the text measurer.
206.81 + /// </summary>
206.82 + /// <value>
206.83 + /// The text measurer.
206.84 + /// </value>
206.85 + public IRenderContext TextMeasurer { get; set; }
206.86 +
206.87 + /// <summary>
206.88 + /// Closes the svg writer.
206.89 + /// </summary>
206.90 + public void Close()
206.91 + {
206.92 + this.w.Close();
206.93 + }
206.94 +
206.95 + /// <summary>
206.96 + /// Completes the svg element.
206.97 + /// </summary>
206.98 + public void Complete()
206.99 + {
206.100 + this.w.Complete();
206.101 + }
206.102 +
206.103 + /// <summary>
206.104 + /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
206.105 + /// </summary>
206.106 + public void Dispose()
206.107 + {
206.108 + this.Dispose(true);
206.109 + GC.SuppressFinalize(this);
206.110 + }
206.111 +
206.112 + /// <summary>
206.113 + /// Draws an ellipse.
206.114 + /// </summary>
206.115 + /// <param name="rect">The rectangle.</param>
206.116 + /// <param name="fill">The fill color.</param>
206.117 + /// <param name="stroke">The stroke color.</param>
206.118 + /// <param name="thickness">The thickness.</param>
206.119 + public override void DrawEllipse(OxyRect rect, OxyColor fill, OxyColor stroke, double thickness)
206.120 + {
206.121 + this.w.WriteEllipse(
206.122 + rect.Left, rect.Top, rect.Width, rect.Height, this.w.CreateStyle(fill, stroke, thickness));
206.123 + }
206.124 +
206.125 + /// <summary>
206.126 + /// Draws the polyline from the specified points.
206.127 + /// </summary>
206.128 + /// <param name="points">The points.</param>
206.129 + /// <param name="stroke">The stroke color.</param>
206.130 + /// <param name="thickness">The stroke thickness.</param>
206.131 + /// <param name="dashArray">The dash array.</param>
206.132 + /// <param name="lineJoin">The line join type.</param>
206.133 + /// <param name="aliased">if set to <c>true</c> the shape will be aliased.</param>
206.134 + public override void DrawLine(
206.135 + IList<ScreenPoint> points,
206.136 + OxyColor stroke,
206.137 + double thickness,
206.138 + double[] dashArray,
206.139 + OxyPenLineJoin lineJoin,
206.140 + bool aliased)
206.141 + {
206.142 + this.w.WritePolyline(points, this.w.CreateStyle(null, stroke, thickness, dashArray, lineJoin));
206.143 + }
206.144 +
206.145 + /// <summary>
206.146 + /// Draws the polygon from the specified points. The polygon can have stroke and/or fill.
206.147 + /// </summary>
206.148 + /// <param name="points">The points.</param>
206.149 + /// <param name="fill">The fill color.</param>
206.150 + /// <param name="stroke">The stroke color.</param>
206.151 + /// <param name="thickness">The stroke thickness.</param>
206.152 + /// <param name="dashArray">The dash array.</param>
206.153 + /// <param name="lineJoin">The line join type.</param>
206.154 + /// <param name="aliased">if set to <c>true</c> the shape will be aliased.</param>
206.155 + public override void DrawPolygon(
206.156 + IList<ScreenPoint> points,
206.157 + OxyColor fill,
206.158 + OxyColor stroke,
206.159 + double thickness,
206.160 + double[] dashArray,
206.161 + OxyPenLineJoin lineJoin,
206.162 + bool aliased)
206.163 + {
206.164 + this.w.WritePolygon(points, this.w.CreateStyle(fill, stroke, thickness, dashArray, lineJoin));
206.165 + }
206.166 +
206.167 + /// <summary>
206.168 + /// Draws the rectangle.
206.169 + /// </summary>
206.170 + /// <param name="rect">The rectangle.</param>
206.171 + /// <param name="fill">The fill color.</param>
206.172 + /// <param name="stroke">The stroke color.</param>
206.173 + /// <param name="thickness">The stroke thickness.</param>
206.174 + public override void DrawRectangle(OxyRect rect, OxyColor fill, OxyColor stroke, double thickness)
206.175 + {
206.176 + this.w.WriteRectangle(
206.177 + rect.Left, rect.Top, rect.Width, rect.Height, this.w.CreateStyle(fill, stroke, thickness));
206.178 + }
206.179 +
206.180 + /// <summary>
206.181 + /// Draws the text.
206.182 + /// </summary>
206.183 + /// <param name="p">The p.</param>
206.184 + /// <param name="text">The text.</param>
206.185 + /// <param name="c">The c.</param>
206.186 + /// <param name="fontFamily">The font family.</param>
206.187 + /// <param name="fontSize">Size of the font.</param>
206.188 + /// <param name="fontWeight">The font weight.</param>
206.189 + /// <param name="rotate">The rotate.</param>
206.190 + /// <param name="halign">The horizontal alignment.</param>
206.191 + /// <param name="valign">The vertical alignment.</param>
206.192 + /// <param name="maxSize">Size of the max.</param>
206.193 + public override void DrawText(
206.194 + ScreenPoint p,
206.195 + string text,
206.196 + OxyColor c,
206.197 + string fontFamily,
206.198 + double fontSize,
206.199 + double fontWeight,
206.200 + double rotate,
206.201 + HorizontalAlignment halign,
206.202 + VerticalAlignment valign,
206.203 + OxySize? maxSize)
206.204 + {
206.205 + if (string.IsNullOrEmpty(text))
206.206 + {
206.207 + return;
206.208 + }
206.209 +
206.210 + var lines = Regex.Split(text, "\r\n");
206.211 + if (valign == VerticalAlignment.Bottom)
206.212 + {
206.213 + for (var i = lines.Length - 1; i >= 0; i--)
206.214 + {
206.215 + var line = lines[i];
206.216 + var size = this.MeasureText(line, fontFamily, fontSize, fontWeight);
206.217 + this.w.WriteText(p, line, c, fontFamily, fontSize, fontWeight, rotate, halign, valign);
206.218 +
206.219 + p.X += Math.Sin(rotate / 180.0 * Math.PI) * size.Height;
206.220 + p.Y -= Math.Cos(rotate / 180.0 * Math.PI) * size.Height;
206.221 + }
206.222 + }
206.223 + else
206.224 + {
206.225 + foreach (var line in lines)
206.226 + {
206.227 + var size = this.MeasureText(line, fontFamily, fontSize, fontWeight);
206.228 + this.w.WriteText(p, line, c, fontFamily, fontSize, fontWeight, rotate, halign, valign);
206.229 +
206.230 + p.X -= Math.Sin(rotate / 180.0 * Math.PI) * size.Height;
206.231 + p.Y += Math.Cos(rotate / 180.0 * Math.PI) * size.Height;
206.232 + }
206.233 + }
206.234 + }
206.235 +
206.236 + /// <summary>
206.237 + /// Flushes this instance.
206.238 + /// </summary>
206.239 + public void Flush()
206.240 + {
206.241 + this.w.Flush();
206.242 + }
206.243 +
206.244 + /// <summary>
206.245 + /// Measures the text.
206.246 + /// </summary>
206.247 + /// <param name="text">The text.</param>
206.248 + /// <param name="fontFamily">The font family.</param>
206.249 + /// <param name="fontSize">Size of the font.</param>
206.250 + /// <param name="fontWeight">The font weight.</param>
206.251 + /// <returns>
206.252 + /// The text size.
206.253 + /// </returns>
206.254 + public override OxySize MeasureText(string text, string fontFamily, double fontSize, double fontWeight)
206.255 + {
206.256 + if (string.IsNullOrEmpty(text))
206.257 + {
206.258 + return OxySize.Empty;
206.259 + }
206.260 +
206.261 + return this.TextMeasurer.MeasureText(text, fontFamily, fontSize, fontWeight);
206.262 + }
206.263 +
206.264 + /// <summary>
206.265 + /// Releases unmanaged and - optionally - managed resources
206.266 + /// </summary>
206.267 + /// <param name="disposing"><c>true</c> to release both managed and unmanaged resources; <c>false</c> to release only unmanaged resources.</param>
206.268 + private void Dispose(bool disposing)
206.269 + {
206.270 + if (!this.disposed)
206.271 + {
206.272 + if (disposing)
206.273 + {
206.274 + this.w.Dispose();
206.275 + }
206.276 + }
206.277 +
206.278 + this.disposed = true;
206.279 + }
206.280 + }
206.281 +}
206.282 \ No newline at end of file
207.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
207.2 +++ b/External/OxyPlot/OxyPlot/Svg/SvgWriter.cs Sat Jun 08 16:53:22 2013 +0000
207.3 @@ -0,0 +1,502 @@
207.4 +// --------------------------------------------------------------------------------------------------------------------
207.5 +// <copyright file="SvgWriter.cs" company="OxyPlot">
207.6 +// The MIT License (MIT)
207.7 +//
207.8 +// Copyright (c) 2012 Oystein Bjorke
207.9 +//
207.10 +// Permission is hereby granted, free of charge, to any person obtaining a
207.11 +// copy of this software and associated documentation files (the
207.12 +// "Software"), to deal in the Software without restriction, including
207.13 +// without limitation the rights to use, copy, modify, merge, publish,
207.14 +// distribute, sublicense, and/or sell copies of the Software, and to
207.15 +// permit persons to whom the Software is furnished to do so, subject to
207.16 +// the following conditions:
207.17 +//
207.18 +// The above copyright notice and this permission notice shall be included
207.19 +// in all copies or substantial portions of the Software.
207.20 +//
207.21 +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
207.22 +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
207.23 +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
207.24 +// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
207.25 +// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
207.26 +// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
207.27 +// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
207.28 +// </copyright>
207.29 +// <summary>
207.30 +// Scalable Vector Graphics writer.
207.31 +// </summary>
207.32 +// --------------------------------------------------------------------------------------------------------------------
207.33 +namespace OxyPlot
207.34 +{
207.35 + using System;
207.36 + using System.Collections.Generic;
207.37 + using System.Globalization;
207.38 + using System.IO;
207.39 + using System.Text;
207.40 +
207.41 + /// <summary>
207.42 + /// Represents a writer that provides easy generation of Scalable Vector Graphics files.
207.43 + /// </summary>
207.44 + public class SvgWriter : XmlWriterBase
207.45 + {
207.46 + /// <summary>
207.47 + /// The end is written.
207.48 + /// </summary>
207.49 + private bool endIsWritten;
207.50 +
207.51 + /// <summary>
207.52 + /// Initializes a new instance of the <see cref="SvgWriter"/> class.
207.53 + /// </summary>
207.54 + /// <param name="stream">
207.55 + /// The stream.
207.56 + /// </param>
207.57 + /// <param name="width">
207.58 + /// The width.
207.59 + /// </param>
207.60 + /// <param name="height">
207.61 + /// The height.
207.62 + /// </param>
207.63 + /// <param name="isDocument">
207.64 + /// if set to <c>true</c>, the writer will write the xml headers (?xml and !DOCTYPE).
207.65 + /// </param>
207.66 + public SvgWriter(Stream stream, double width, double height, bool isDocument = true)
207.67 + : base(stream)
207.68 + {
207.69 + this.IsDocument = isDocument;
207.70 + this.NumberFormat = "0.####";
207.71 + this.WriteHeader(width, height);
207.72 + }
207.73 +
207.74 + /// <summary>
207.75 + /// Gets or sets a value indicating whether this writer should produce a stand-alone document.
207.76 + /// </summary>
207.77 + public bool IsDocument { get; set; }
207.78 +
207.79 + /// <summary>
207.80 + /// Gets or sets the number format.
207.81 + /// </summary>
207.82 + /// <value>The number format.</value>
207.83 + public string NumberFormat { get; set; }
207.84 +
207.85 + /// <summary>
207.86 + /// Closes the svg document.
207.87 + /// </summary>
207.88 + public override void Close()
207.89 + {
207.90 + if (!this.endIsWritten)
207.91 + {
207.92 + this.Complete();
207.93 + }
207.94 +
207.95 + base.Close();
207.96 + }
207.97 +
207.98 + /// <summary>
207.99 + /// Writes the end of the document.
207.100 + /// </summary>
207.101 + public void Complete()
207.102 + {
207.103 + this.WriteEndElement();
207.104 + if (this.IsDocument)
207.105 + {
207.106 + this.WriteEndDocument();
207.107 + }
207.108 +
207.109 + this.endIsWritten = true;
207.110 + }
207.111 +
207.112 + /// <summary>
207.113 + /// Creates a style.
207.114 + /// </summary>
207.115 + /// <param name="fill">
207.116 + /// The fill color.
207.117 + /// </param>
207.118 + /// <param name="stroke">
207.119 + /// The stroke color.
207.120 + /// </param>
207.121 + /// <param name="thickness">
207.122 + /// The stroke thickness.
207.123 + /// </param>
207.124 + /// <param name="dashArray">
207.125 + /// The line dash array.
207.126 + /// </param>
207.127 + /// <param name="lineJoin">
207.128 + /// The line join type.
207.129 + /// </param>
207.130 + /// <returns>
207.131 + /// A style string.
207.132 + /// </returns>
207.133 + public string CreateStyle(
207.134 + OxyColor fill,
207.135 + OxyColor stroke,
207.136 + double thickness,
207.137 + double[] dashArray = null,
207.138 + OxyPenLineJoin lineJoin = OxyPenLineJoin.Miter)
207.139 + {
207.140 + // http://oreilly.com/catalog/svgess/chapter/ch03.html
207.141 + var style = new StringBuilder();
207.142 + if (fill == null)
207.143 + {
207.144 + style.AppendFormat("fill:none;");
207.145 + }
207.146 + else
207.147 + {
207.148 + style.AppendFormat("fill:{0};", this.ColorToString(fill));
207.149 + if (fill.A != 0xFF)
207.150 + {
207.151 + style.AppendFormat(CultureInfo.InvariantCulture, "fill-opacity:{0};", fill.A / 255.0);
207.152 + }
207.153 + }
207.154 +
207.155 + if (stroke == null)
207.156 + {
207.157 + style.AppendFormat("stroke:none;");
207.158 + }
207.159 + else
207.160 + {
207.161 + string formatString = "stroke:{0};stroke-width:{1:" + this.NumberFormat + "}";
207.162 + style.AppendFormat(formatString, this.ColorToString(stroke), thickness);
207.163 + switch (lineJoin)
207.164 + {
207.165 + case OxyPenLineJoin.Round:
207.166 + style.AppendFormat(";stroke-linejoin:round");
207.167 + break;
207.168 + case OxyPenLineJoin.Bevel:
207.169 + style.AppendFormat(";stroke-linejoin:bevel");
207.170 + break;
207.171 + }
207.172 +
207.173 + if (stroke.A != 0xFF)
207.174 + {
207.175 + style.AppendFormat(CultureInfo.InvariantCulture, ";stroke-opacity:{0}", stroke.A / 255.0);
207.176 + }
207.177 +
207.178 + if (dashArray != null && dashArray.Length > 0)
207.179 + {
207.180 + style.Append(";stroke-dasharray:");
207.181 + for (int i = 0; i < dashArray.Length; i++)
207.182 + {
207.183 + style.AppendFormat(
207.184 + CultureInfo.InvariantCulture, "{0}{1}", i > 0 ? "," : string.Empty, dashArray[i]);
207.185 + }
207.186 + }
207.187 + }
207.188 +
207.189 + return style.ToString();
207.190 + }
207.191 +
207.192 + /// <summary>
207.193 + /// Writes an ellipse.
207.194 + /// </summary>
207.195 + /// <param name="x">
207.196 + /// The x coordinate of the center.
207.197 + /// </param>
207.198 + /// <param name="y">
207.199 + /// The y coordinate of the center.
207.200 + /// </param>
207.201 + /// <param name="width">
207.202 + /// The width.
207.203 + /// </param>
207.204 + /// <param name="height">
207.205 + /// The height.
207.206 + /// </param>
207.207 + /// <param name="style">
207.208 + /// The style.
207.209 + /// </param>
207.210 + public void WriteEllipse(double x, double y, double width, double height, string style)
207.211 + {
207.212 + // http://www.w3.org/TR/SVG/shapes.html#EllipseElement
207.213 + this.WriteStartElement("ellipse");
207.214 + this.WriteAttributeString("cx", x + (width / 2));
207.215 + this.WriteAttributeString("cy", y + (height / 2));
207.216 + this.WriteAttributeString("rx", width / 2);
207.217 + this.WriteAttributeString("ry", height / 2);
207.218 + this.WriteAttributeString("style", style);
207.219 + this.WriteEndElement();
207.220 + }
207.221 +
207.222 + /// <summary>
207.223 + /// Writes a line.
207.224 + /// </summary>
207.225 + /// <param name="p1">
207.226 + /// The first point.
207.227 + /// </param>
207.228 + /// <param name="p2">
207.229 + /// The second point.
207.230 + /// </param>
207.231 + /// <param name="style">
207.232 + /// The style.
207.233 + /// </param>
207.234 + public void WriteLine(ScreenPoint p1, ScreenPoint p2, string style)
207.235 + {
207.236 + // http://www.w3.org/TR/SVG/shapes.html#LineElement
207.237 + // http://www.w3schools.com/svg/svg_line.asp
207.238 + this.WriteStartElement("line");
207.239 + this.WriteAttributeString("x1", p1.X);
207.240 + this.WriteAttributeString("y1", p1.Y);
207.241 + this.WriteAttributeString("x2", p2.X);
207.242 + this.WriteAttributeString("y2", p2.Y);
207.243 + this.WriteAttributeString("style", style);
207.244 + this.WriteEndElement();
207.245 + }
207.246 +
207.247 + /// <summary>
207.248 + /// Writes a polygon.
207.249 + /// </summary>
207.250 + /// <param name="points">
207.251 + /// The points.
207.252 + /// </param>
207.253 + /// <param name="style">
207.254 + /// The style.
207.255 + /// </param>
207.256 + public void WritePolygon(IEnumerable<ScreenPoint> points, string style)
207.257 + {
207.258 + // http://www.w3.org/TR/SVG/shapes.html#PolygonElement
207.259 + this.WriteStartElement("polygon");
207.260 + this.WriteAttributeString("points", this.PointsToString(points));
207.261 + this.WriteAttributeString("style", style);
207.262 + this.WriteEndElement();
207.263 + }
207.264 +
207.265 + /// <summary>
207.266 + /// Writes a polyline.
207.267 + /// </summary>
207.268 + /// <param name="pts">
207.269 + /// The points.
207.270 + /// </param>
207.271 + /// <param name="style">
207.272 + /// The style.
207.273 + /// </param>
207.274 + public void WritePolyline(IEnumerable<ScreenPoint> pts, string style)
207.275 + {
207.276 + // http://www.w3.org/TR/SVG/shapes.html#PolylineElement
207.277 + this.WriteStartElement("polyline");
207.278 + this.WriteAttributeString("points", this.PointsToString(pts));
207.279 + this.WriteAttributeString("style", style);
207.280 + this.WriteEndElement();
207.281 + }
207.282 +
207.283 + /// <summary>
207.284 + /// Writes a rectangle.
207.285 + /// </summary>
207.286 + /// <param name="x">
207.287 + /// The x coordinate.
207.288 + /// </param>
207.289 + /// <param name="y">
207.290 + /// The y coordinate.
207.291 + /// </param>
207.292 + /// <param name="width">
207.293 + /// The width.
207.294 + /// </param>
207.295 + /// <param name="height">
207.296 + /// The height.
207.297 + /// </param>
207.298 + /// <param name="style">
207.299 + /// The style.
207.300 + /// </param>
207.301 + public void WriteRectangle(double x, double y, double width, double height, string style)
207.302 + {
207.303 + // http://www.w3.org/TR/SVG/shapes.html#RectangleElement
207.304 + this.WriteStartElement("rect");
207.305 + this.WriteAttributeString("x", x);
207.306 + this.WriteAttributeString("y", y);
207.307 + this.WriteAttributeString("width", width);
207.308 + this.WriteAttributeString("height", height);
207.309 + this.WriteAttributeString("style", style);
207.310 + this.WriteEndElement();
207.311 + }
207.312 +
207.313 + /// <summary>
207.314 + /// Writes text.
207.315 + /// </summary>
207.316 + /// <param name="position">
207.317 + /// The position.
207.318 + /// </param>
207.319 + /// <param name="text">
207.320 + /// The text.
207.321 + /// </param>
207.322 + /// <param name="fill">
207.323 + /// The text color.
207.324 + /// </param>
207.325 + /// <param name="fontFamily">
207.326 + /// The font family.
207.327 + /// </param>
207.328 + /// <param name="fontSize">
207.329 + /// The font size.
207.330 + /// </param>
207.331 + /// <param name="fontWeight">
207.332 + /// The font weight.
207.333 + /// </param>
207.334 + /// <param name="rotate">
207.335 + /// The rotation angle.
207.336 + /// </param>
207.337 + /// <param name="halign">
207.338 + /// The horizontal alignment.
207.339 + /// </param>
207.340 + /// <param name="valign">
207.341 + /// The vertical alignment.
207.342 + /// </param>
207.343 + public void WriteText(
207.344 + ScreenPoint position,
207.345 + string text,
207.346 + OxyColor fill,
207.347 + string fontFamily = null,
207.348 + double fontSize = 10,
207.349 + double fontWeight = FontWeights.Normal,
207.350 + double rotate = 0,
207.351 + HorizontalAlignment halign = HorizontalAlignment.Left,
207.352 + VerticalAlignment valign = VerticalAlignment.Top)
207.353 + {
207.354 + // http://www.w3.org/TR/SVG/text.html
207.355 + this.WriteStartElement("text");
207.356 +
207.357 + // WriteAttributeString("x", position.X);
207.358 + // WriteAttributeString("y", position.Y);
207.359 + string baselineAlignment = "hanging";
207.360 + if (valign == VerticalAlignment.Middle)
207.361 + {
207.362 + baselineAlignment = "middle";
207.363 + }
207.364 +
207.365 + if (valign == VerticalAlignment.Bottom)
207.366 + {
207.367 + baselineAlignment = "baseline";
207.368 + }
207.369 +
207.370 + this.WriteAttributeString("dominant-baseline", baselineAlignment);
207.371 +
207.372 + string textAnchor = "start";
207.373 + if (halign == HorizontalAlignment.Center)
207.374 + {
207.375 + textAnchor = "middle";
207.376 + }
207.377 +
207.378 + if (halign == HorizontalAlignment.Right)
207.379 + {
207.380 + textAnchor = "end";
207.381 + }
207.382 +
207.383 + this.WriteAttributeString("text-anchor", textAnchor);
207.384 +
207.385 + string fmt = "translate({0:" + this.NumberFormat + "},{1:" + this.NumberFormat + "})";
207.386 + string transform = string.Format(CultureInfo.InvariantCulture, fmt, position.X, position.Y);
207.387 + if (Math.Abs(rotate) > 0)
207.388 + {
207.389 + transform += string.Format(CultureInfo.InvariantCulture, " rotate({0})", rotate);
207.390 + }
207.391 +
207.392 + this.WriteAttributeString("transform", transform);
207.393 +
207.394 + if (fontFamily != null)
207.395 + {
207.396 + this.WriteAttributeString("font-family", fontFamily);
207.397 + }
207.398 +
207.399 + if (fontSize > 0)
207.400 + {
207.401 + this.WriteAttributeString("font-size", fontSize);
207.402 + }
207.403 +
207.404 + if (fontWeight > 0)
207.405 + {
207.406 + this.WriteAttributeString("font-weight", fontWeight);
207.407 + }
207.408 +
207.409 + this.WriteAttributeString("fill", this.ColorToString(fill));
207.410 +
207.411 + // WriteAttributeString("style", style);
207.412 + this.WriteString(text);
207.413 + this.WriteEndElement();
207.414 + }
207.415 +
207.416 + /// <summary>
207.417 + /// Converts a color to a svg color string.
207.418 + /// </summary>
207.419 + /// <param name="color">The color.</param>
207.420 + /// <returns>The color string.</returns>
207.421 + protected string ColorToString(OxyColor color)
207.422 + {
207.423 + if (color == OxyColors.Black)
207.424 + {
207.425 + return "black";
207.426 + }
207.427 +
207.428 + var formatString = "rgb({0:" + this.NumberFormat + "},{1:" + this.NumberFormat + "},{2:" + this.NumberFormat + "})";
207.429 + return string.Format(formatString, color.R, color.G, color.B);
207.430 + }
207.431 +
207.432 + /// <summary>
207.433 + /// The write attribute string.
207.434 + /// </summary>
207.435 + /// <param name="name">
207.436 + /// The name.
207.437 + /// </param>
207.438 + /// <param name="value">
207.439 + /// The value.
207.440 + /// </param>
207.441 + protected void WriteAttributeString(string name, double value)
207.442 + {
207.443 + this.WriteAttributeString(name, value.ToString(this.NumberFormat, CultureInfo.InvariantCulture));
207.444 + }
207.445 +
207.446 + /// <summary>
207.447 + /// Converts a value to a string or to the specified "auto" string if the value is NaN.
207.448 + /// </summary>
207.449 + /// <param name="value">The value.</param>
207.450 + /// <param name="auto">The string to return if value is NaN.</param>
207.451 + /// <returns>A string.</returns>
207.452 + private string GetAutoValue(double value, string auto)
207.453 + {
207.454 + if (double.IsNaN(value))
207.455 + {
207.456 + return auto;
207.457 + }
207.458 +
207.459 + return value.ToString(this.NumberFormat, CultureInfo.InvariantCulture);
207.460 + }
207.461 +
207.462 + /// <summary>
207.463 + /// Converts a list of points to a string.
207.464 + /// </summary>
207.465 + /// <param name="points">The points.</param>
207.466 + /// <returns>A string.</returns>
207.467 + private string PointsToString(IEnumerable<ScreenPoint> points)
207.468 + {
207.469 + var sb = new StringBuilder();
207.470 + string fmt = "{0:" + this.NumberFormat + "},{1:" + this.NumberFormat + "} ";
207.471 + foreach (var p in points)
207.472 + {
207.473 + sb.AppendFormat(CultureInfo.InvariantCulture, fmt, p.X, p.Y);
207.474 + }
207.475 +
207.476 + return sb.ToString().Trim();
207.477 + }
207.478 +
207.479 + /// <summary>
207.480 + /// The write header.
207.481 + /// </summary>
207.482 + /// <param name="width">
207.483 + /// The width.
207.484 + /// </param>
207.485 + /// <param name="height">
207.486 + /// The height.
207.487 + /// </param>
207.488 + private void WriteHeader(double width, double height)
207.489 + {
207.490 + // http://www.w3.org/TR/SVG/struct.html#SVGElement
207.491 + if (this.IsDocument)
207.492 + {
207.493 + this.WriteStartDocument(false);
207.494 + this.WriteDocType(
207.495 + "svg", "-//W3C//DTD SVG 1.1//EN", "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd", null);
207.496 + }
207.497 +
207.498 + this.WriteStartElement("svg", "http://www.w3.org/2000/svg");
207.499 + this.WriteAttributeString("width", this.GetAutoValue(width, "100%"));
207.500 + this.WriteAttributeString("height", this.GetAutoValue(height, "100%"));
207.501 + this.WriteAttributeString("version", "1.1");
207.502 + }
207.503 +
207.504 + }
207.505 +}
207.506 \ No newline at end of file