예제 #1
0
        public void Render()
        {
            try
            {
                double CanvasWidth  = (ActualWidth - 24) * Zoom;
                double CanvasHeight = Height - 14;

                CanvasPlot.Children.Clear();

                if (CanvasWidth <= 0 || CanvasHeight <= 0)
                {
                    return;
                }

                #region Determine axis range

                ValueMin = double.MaxValue;
                ValueMax = -double.MaxValue;

                if (!double.IsNaN(AxisMin))
                {
                    ValueMin = AxisMin;
                }
                else if (Points != null && Points.Count > 0)
                {
                    foreach (var point in Points)
                    {
                        if (!double.IsNaN(point.Value))
                        {
                            ValueMin = Math.Min(ValueMin, point.Value);
                        }
                    }
                }
                else
                {
                    ValueMin = 0;
                }

                if (!double.IsNaN(AxisMax))
                {
                    ValueMax = AxisMax;
                }
                else if (Points != null && Points.Count > 0 && Points.Any(v => !double.IsNaN(v.Value)))
                {
                    foreach (var point in Points)
                    {
                        if (!double.IsNaN(point.Value))
                        {
                            ValueMax = Math.Max(ValueMax, point.Value);
                        }
                    }
                }
                else
                {
                    ValueMax = 1;
                }

                double Range = ValueMax - ValueMin;

                if (ValueMin == ValueMax) // Range = 0, probably only one point
                {
                    ValueMax += 1;
                    ValueMin -= 1;
                }
                else // Make sure there are a few pixels left to draw the points at the extremes
                {
                    if (double.IsNaN(AxisMax))
                    {
                        ValueMax += Range / CanvasHeight * PointRadius;
                    }
                    if (double.IsNaN(AxisMin))
                    {
                        ValueMin -= Range / CanvasHeight * PointRadius;
                    }
                }

                Range = ValueMax - ValueMin;

                Dispatcher.Invoke(() =>
                {
                    string FloatFormat = "F0";
                    if (Math.Max(ValueMax, ValueMin) < 100)
                    {
                        FloatFormat = "F1";
                    }
                    if (Math.Max(ValueMax, ValueMin) < 10)
                    {
                        FloatFormat = "F2";
                    }

                    TextLineBottom.Text = ValueMin.ToString(FloatFormat, CultureInfo.InvariantCulture);
                    TextLineCenter.Text = ((ValueMin + ValueMax) * 0.5).ToString(FloatFormat, CultureInfo.InvariantCulture);
                    TextLineTop.Text    = ValueMax.ToString(FloatFormat, CultureInfo.InvariantCulture);
                });

                #endregion

                #region Adjust range highlight

                double RangeHighlightClampedMin = Math.Max(ValueMin, RangeHighlightMin);
                double RangeHighlightClampedMax = Math.Min(ValueMax, RangeHighlightMax);

                PanelRangeHighlight.Margin = new Thickness(0, 7 + (ValueMax - RangeHighlightClampedMax) / Range * CanvasHeight, 0, 0);
                PanelRangeHighlight.Height = Math.Max(0, RangeHighlightClampedMax - RangeHighlightClampedMin) / Range * CanvasHeight;

                #endregion

                if (Range < 0 || Points == null || Points.Count == 0)
                {
                    ImagePlot.Source = null;
                    return;
                }

                float[] HistogramBins = new float[50];

                DrawingGroup DGroup = new DrawingGroup();
                using (DrawingContext DContext = DGroup.Open())
                {
                    DContext.PushClip(new RectangleGeometry(new Rect(new Size(CanvasWidth, CanvasHeight))));

                    Pen OutlinePen = new Pen(Brushes.Transparent, 0);
                    OutlinePen.Freeze();

                    SolidColorBrush BackgroundBrush = new SolidColorBrush(Colors.Transparent);
                    BackgroundBrush.Freeze();
                    DContext.DrawRectangle(BackgroundBrush, OutlinePen, new Rect(new Size(CanvasWidth, CanvasHeight)));

                    SolidColorBrush[] ColorBrushes = PointColors.Count > 0
                                                         ? PointColors.Select(c =>
                    {
                        SolidColorBrush Brush = new SolidColorBrush(Color.FromArgb(255, c.R, c.G, c.B));
                        Brush.Freeze();
                        return(Brush);
                    }).ToArray()
                                                         : new[] { new SolidColorBrush(Color.FromArgb(150, Colors.DeepSkyBlue.R, Colors.DeepSkyBlue.G, Colors.DeepSkyBlue.B)) };

                    StepX   = (CanvasWidth - PointRadius * 2) / Points.Count;
                    OffsetX = StepX / 2 + PointRadius;
                    StepY   = CanvasHeight / Range;

                    PointCenters = new System.Windows.Point[Points.Count];

                    for (int i = 0; i < Points.Count; i++)
                    {
                        if (double.IsNaN(Points[i].Value))
                        {
                            continue;
                        }

                        double X = i * StepX + OffsetX;
                        double Y = (ValueMax - Points[i].Value) * StepY;

                        DContext.DrawEllipse(ColorBrushes[Points[i].ColorID], OutlinePen, new System.Windows.Point(X, Y), PointRadius, PointRadius);

                        PointCenters[i] = new System.Windows.Point(X, Y);

                        HistogramBins[Math.Max(0, Math.Min(HistogramBins.Length - 1, (int)((Points[i].Value - ValueMin) / Range * (HistogramBins.Length - 1) + 0.5)))]++;
                    }
                }

                DrawingImage Plot = new DrawingImage(DGroup);
                Plot.Freeze();
                Dispatcher.Invoke(() => ImagePlot.Source = Plot);

                Dispatcher.Invoke(() =>
                {
                    float[] HistogramConv = new float[HistogramBins.Length];
                    float[] ConvKernel    = { 0.11f, 0.37f, 0.78f, 1f, 0.78f, 0.37f, 0.11f };
                    for (int i = 0; i < HistogramBins.Length; i++)
                    {
                        float Sum     = 0;
                        float Samples = 0;
                        for (int j = 0; j < ConvKernel.Length; j++)
                        {
                            int ij = i - 3 + j;
                            if (ij < 0 || ij >= HistogramBins.Length)
                            {
                                continue;
                            }
                            Sum     += ConvKernel[j] * HistogramBins[ij];
                            Samples += ConvKernel[j];
                        }
                        HistogramConv[i] = Sum / Samples;
                    }

                    float HistogramMax = MathHelper.Max(HistogramConv);
                    if (HistogramMax > 0)
                    {
                        HistogramConv = HistogramConv.Select(v => v / HistogramMax * 16).ToArray();
                    }

                    Polygon HistogramPolygon = new Polygon()
                    {
                        Stroke  = Brushes.Transparent,
                        Fill    = Brushes.Gray,
                        Opacity = 0.15
                    };
                    PointCollection HistogramPoints = new PointCollection(HistogramConv.Length);

                    HistogramPoints.Add(new System.Windows.Point(16, 0));
                    HistogramPoints.Add(new System.Windows.Point(16, CanvasHeight));
                    for (int i = 0; i < HistogramConv.Length; i++)
                    {
                        double X = 15 - HistogramConv[i];
                        double Y = CanvasHeight - (i / (float)(HistogramConv.Length - 1) * CanvasHeight);
                        HistogramPoints.Add(new System.Windows.Point(X, Y));
                    }

                    HistogramPolygon.Points = HistogramPoints;

                    CanvasHistogram.Children.Clear();
                    CanvasHistogram.Children.Add(HistogramPolygon);
                    Canvas.SetRight(HistogramPolygon, 0);
                });
            }
            catch
            {
            }
        }
예제 #2
0
        public void Render()
        {
            try
            {
                double CanvasWidth  = ActualWidth;
                double CanvasHeight = ActualHeight;
                double FullRange    = AxisMax * 2;

                CanvasPlot.Children.Clear();

                if (double.IsNaN(AxisMax))
                {
                    return;
                }

                if (CanvasWidth <= 0 || CanvasHeight <= 0)
                {
                    return;
                }

                if (Points == null || Points.Count == 0)
                {
                    ImagePlot.Source = null;
                    return;
                }

                DrawingGroup DGroup = new DrawingGroup();
                using (DrawingContext DContext = DGroup.Open())
                {
                    DContext.PushClip(new RectangleGeometry(new Rect(new Size(CanvasWidth, CanvasHeight))));

                    Pen OutlinePen = new Pen(Brushes.Transparent, 0);
                    OutlinePen.Freeze();

                    SolidColorBrush BackgroundBrush = new SolidColorBrush(Colors.Transparent);
                    BackgroundBrush.Freeze();
                    DContext.DrawRectangle(BackgroundBrush, OutlinePen, new Rect(new Size(CanvasWidth, CanvasHeight)));

                    SolidColorBrush[] ColorBrushes = PointColors.Count > 0
                                                         ? PointColors.Select(c =>
                    {
                        SolidColorBrush Brush = new SolidColorBrush(Color.FromArgb(120, c.R, c.G, c.B));
                        Brush.Freeze();
                        return(Brush);
                    }).ToArray()
                                                         : new[] { new SolidColorBrush(Color.FromArgb(150, Colors.DeepSkyBlue.R, Colors.DeepSkyBlue.G, Colors.DeepSkyBlue.B)) };

                    PointCenters = new System.Windows.Point[Points.Count];

                    for (int i = 0; i < Points.Count; i++)
                    {
                        if (double.IsNaN(Points[i].X) || double.IsNaN(Points[i].Y))
                        {
                            continue;
                        }

                        //if (Math.Abs(Points[i].X) > AxisMax || Math.Abs(Points[i].Y) > AxisMax)
                        //    continue;

                        double X = Points[i].X / FullRange * CanvasWidth + CanvasWidth / 2;
                        double Y = Points[i].Y / FullRange * CanvasHeight + CanvasHeight / 2;

                        DContext.DrawEllipse(ColorBrushes[Points[i].ColorID], OutlinePen, new System.Windows.Point(X, Y), PointRadius, PointRadius);

                        PointCenters[i] = new System.Windows.Point(X, Y);
                    }
                }

                DrawingImage Plot = new DrawingImage(DGroup);
                Plot.Freeze();
                Dispatcher.Invoke(() => ImagePlot.Source = Plot);
            }
            catch
            {
            }
        }