/// <summary> Adds a value to the Chart Line </summary>
        /// <param name="value">progress value</param>
        public void AddValue(ChartLine line, double value)
        {
            if (double.IsNaN(value))
            {
                line.DrawValues.Insert(0, 0);
            }
            else
            {
                // Insert at first position; Negative values are flatten to 0 (zero)
                line.DrawValues.Insert(0, Math.Max(value, 0F));
            }

            // Remove last item if maximum value count is reached
            if (line.DrawValues.Count > MAX_VALUE_COUNT)
            {
                line.DrawValues.RemoveAt(MAX_VALUE_COUNT);
            }

            // Calculate horizontal grid offset for "scrolling" effect
            gridScrollOffset += line.ValueSpacing;
            if (gridScrollOffset > GRID_SPACING)
            {
                gridScrollOffset = gridScrollOffset % GRID_SPACING;
            }

            Invalidate();
        }
        /// <summary>
        /// Calculates the vertical Position of a value in relation the chart size,
        /// Scale Mode and, if ScaleMode is Relative, to the current maximum value
        /// </summary>
        /// <param name="value">performance value</param>
        /// <returns>vertical Point position in Pixels</returns>
        private int CalcVerticalPosition(ChartLine line, decimal value)
        {
            decimal result = Decimal.Zero;

            result = (line.CurrentMaxValue > 0) ? (value * this.MaxChartHeight / (decimal)line.CurrentMaxValue) : 0;
            result = this.Height - result;
            return(Convert.ToInt32(Math.Round(result)));
        }
        /// <summary>
        /// Returns the currently highest (displayed) value, for Relative ScaleMode
        /// </summary>
        /// <returns></returns>
        private double GetHighestValueForRelativeMode(ChartLine line)
        {
            double maxValue = 0;

            for (int i = 0; i < line.VisibleValues; i++)
            {
                // Set if higher then previous max value
                if (line.DrawValues[i] > maxValue)
                {
                    maxValue = line.DrawValues[i];
                }
            }
            return(maxValue);
        }
        private void DrawAverageLine(Graphics g, ChartLine line)
        {
            for (int i = 0; i < line.VisibleValues; i++)
            {
                line.AverageValue += line.DrawValues[i];
            }

            if (!double.IsNaN(line.AverageValue / line.VisibleValues))
            {
                line.AverageValue = line.AverageValue / line.VisibleValues;
            }

            int        verticalPosition = CalcVerticalPosition(line, (decimal)line.AverageValue);
            SolidBrush sb = new SolidBrush(line.ChartLinePen.Color);

            g.DrawString("Avg: " + (int)line.AverageValue + " " + line.AverageComment, this.Font, sb, 2.0f, verticalPosition - 25);
            g.DrawLine(line.ChartLinePen.Pen, 0, verticalPosition, Width, verticalPosition);
        }