source: trunk/sources/HeuristicLab.Problems.DataAnalysis.Trading.Views/3.4/SolutionLineChartView.cs @ 9997

Last change on this file since 9997 was 9997, checked in by gkronber, 6 years ago

#1508 fixed bugs in line chart visualization for the trading plugin

File size: 8.2 KB
Line 
1#region License Information
2/* HeuristicLab
3 * Copyright (C) 2002-2013 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
4 *
5 * This file is part of HeuristicLab.
6 *
7 * HeuristicLab is free software: you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation, either version 3 of the License, or
10 * (at your option) any later version.
11 *
12 * HeuristicLab is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
19 */
20#endregion
21using System;
22using System.Collections.Generic;
23using System.Drawing;
24using System.Linq;
25using System.Windows.Forms;
26using System.Windows.Forms.DataVisualization.Charting;
27using HeuristicLab.MainForm;
28using HeuristicLab.Problems.DataAnalysis.Views;
29
30namespace HeuristicLab.Problems.DataAnalysis.Trading.Views {
31  [View("Line Chart")]
32  [Content(typeof(ISolution))]
33  public partial class SolutionLineChartView : DataAnalysisSolutionEvaluationView, ISolutionEvaluationView {
34    private const string PRICEVARIABLE_SERIES_NAME = "Price";
35    private const string SIGNALS_SERIES_NAME = "Signals";
36    private const string ASSET_SERIES_NAME = "Asset";
37
38
39    public new ISolution Content {
40      get { return (ISolution)base.Content; }
41      set { base.Content = value; }
42    }
43
44    public SolutionLineChartView()
45      : base() {
46      InitializeComponent();
47      //configure axis
48      this.chart.CustomizeAllChartAreas();
49      this.chart.ChartAreas[0].CursorX.IsUserSelectionEnabled = true;
50      this.chart.ChartAreas[0].AxisX.ScaleView.Zoomable = true;
51      this.chart.ChartAreas[0].CursorX.Interval = 1;
52
53      this.chart.ChartAreas[0].CursorY.IsUserSelectionEnabled = true;
54      this.chart.ChartAreas[0].AxisY.ScaleView.Zoomable = true;
55      this.chart.ChartAreas[0].AxisY.IntervalAutoMode = IntervalAutoMode.VariableCount;
56      this.chart.ChartAreas[0].AxisY2.ScaleView.Zoomable = false;
57      this.chart.ChartAreas[0].AxisY2.IntervalAutoMode = IntervalAutoMode.VariableCount;
58      this.chart.ChartAreas[0].AxisY2.LabelStyle.Enabled = false;
59      this.chart.ChartAreas[0].AxisY2.MajorGrid.Enabled = false;
60      this.chart.ChartAreas[0].AxisY2.MinorGrid.Enabled = false;
61      this.chart.ChartAreas[0].AxisY2.MajorTickMark.Enabled = false;
62      this.chart.ChartAreas[0].AxisY2.MinorTickMark.Enabled = false;
63      this.chart.ChartAreas[0].CursorY.Interval = 0;
64    }
65
66    private void RedrawChart() {
67      this.chart.Series.Clear();
68      if (Content != null) {
69        var trainingRows = Content.ProblemData.TrainingIndices;
70        var testRows = Content.ProblemData.TestIndices;
71        this.chart.Series.Add(SIGNALS_SERIES_NAME);
72        this.chart.Series[SIGNALS_SERIES_NAME].YAxisType = AxisType.Secondary;
73        this.chart.Series[SIGNALS_SERIES_NAME].LegendText = SIGNALS_SERIES_NAME;
74        this.chart.Series[SIGNALS_SERIES_NAME].ChartType = SeriesChartType.FastLine;
75        this.chart.Series[SIGNALS_SERIES_NAME].Points.DataBindXY(
76          trainingRows.Concat(testRows).ToArray(),
77          Content.TrainingSignals.Concat(Content.TestSignals).ToArray());
78        this.chart.Series[SIGNALS_SERIES_NAME].Tag = Content;
79
80        var trainingPriceChanges = Content.ProblemData.Dataset.GetDoubleValues(Content.ProblemData.PriceChangeVariable,
81                                                                               trainingRows);
82        var testPriceChanges = Content.ProblemData.Dataset.GetDoubleValues(Content.ProblemData.PriceChangeVariable,
83                                                                               testRows);
84        IEnumerable<double> accumulatedTrainingPrice = GetAccumulatedProfits(trainingPriceChanges);
85        IEnumerable<double> accumulatedTestPrice = GetAccumulatedProfits(testPriceChanges);
86        this.chart.Series.Add(PRICEVARIABLE_SERIES_NAME);
87        this.chart.Series[PRICEVARIABLE_SERIES_NAME].YAxisType = AxisType.Primary;
88        this.chart.Series[PRICEVARIABLE_SERIES_NAME].LegendText = PRICEVARIABLE_SERIES_NAME;
89        this.chart.Series[PRICEVARIABLE_SERIES_NAME].ChartType = SeriesChartType.FastLine;
90        this.chart.Series[PRICEVARIABLE_SERIES_NAME].Points.DataBindXY(
91          trainingRows.Concat(testRows).ToArray(),
92          accumulatedTrainingPrice.Concat(accumulatedTestPrice).ToArray());
93        this.chart.Series[PRICEVARIABLE_SERIES_NAME].Tag = Content;
94
95
96        IEnumerable<double> trainingProfit = OnlineProfitCalculator.GetProfits(trainingPriceChanges, Content.TrainingSignals, Content.ProblemData.TransactionCosts);
97        IEnumerable<double> testProfit = OnlineProfitCalculator.GetProfits(testPriceChanges, Content.TestSignals, Content.ProblemData.TransactionCosts);
98        IEnumerable<double> accTrainingProfit = GetAccumulatedProfits(trainingProfit);
99        IEnumerable<double> accTestProfit = GetAccumulatedProfits(testProfit);
100        this.chart.Series.Add(ASSET_SERIES_NAME);
101        this.chart.Series[ASSET_SERIES_NAME].YAxisType = AxisType.Primary;
102        this.chart.Series[ASSET_SERIES_NAME].LegendText = ASSET_SERIES_NAME;
103        this.chart.Series[ASSET_SERIES_NAME].ChartType = SeriesChartType.FastLine;
104        this.chart.Series[ASSET_SERIES_NAME].Points.DataBindXY(
105          trainingRows.Concat(testRows).ToArray(),
106          accTrainingProfit.Concat(accTestProfit).ToArray());
107        this.chart.Series[ASSET_SERIES_NAME].Tag = Content;
108
109        this.UpdateStripLines();
110      }
111    }
112
113    private IEnumerable<double> GetAccumulatedProfits(IEnumerable<double> xs) {
114      double sum = 0;
115      foreach (var x in xs) {
116        sum += x;
117        yield return sum;
118      }
119    }
120
121    #region events
122    protected override void RegisterContentEvents() {
123      base.RegisterContentEvents();
124      Content.ModelChanged += new EventHandler(Content_ModelChanged);
125      Content.ProblemDataChanged += new EventHandler(Content_ProblemDataChanged);
126    }
127    protected override void DeregisterContentEvents() {
128      base.DeregisterContentEvents();
129      Content.ModelChanged -= new EventHandler(Content_ModelChanged);
130      Content.ProblemDataChanged -= new EventHandler(Content_ProblemDataChanged);
131    }
132
133    private void Content_ProblemDataChanged(object sender, EventArgs e) {
134      RedrawChart();
135    }
136
137    private void Content_ModelChanged(object sender, EventArgs e) {
138      RedrawChart();
139    }
140
141    protected override void OnContentChanged() {
142      base.OnContentChanged();
143      RedrawChart();
144    }
145
146    private void Chart_MouseDoubleClick(object sender, MouseEventArgs e) {
147      HitTestResult result = chart.HitTest(e.X, e.Y);
148      if (result.ChartArea != null && (result.ChartElementType == ChartElementType.PlottingArea ||
149                                       result.ChartElementType == ChartElementType.Gridlines) ||
150                                       result.ChartElementType == ChartElementType.StripLines) {
151        foreach (var axis in result.ChartArea.Axes)
152          axis.ScaleView.ZoomReset(int.MaxValue);
153      }
154    }
155    #endregion
156
157    private void UpdateStripLines() {
158      this.chart.ChartAreas[0].AxisX.StripLines.Clear();
159      this.CreateAndAddStripLine("Training", Color.FromArgb(20, Color.Green),
160        Content.ProblemData.TrainingPartition.Start,
161        Content.ProblemData.TrainingPartition.End);
162      this.CreateAndAddStripLine("Test", Color.FromArgb(20, Color.Red),
163        Content.ProblemData.TestPartition.Start,
164        Content.ProblemData.TestPartition.End);
165    }
166
167    private void CreateAndAddStripLine(string title, Color c, int start, int end) {
168      StripLine stripLine = new StripLine();
169      stripLine.BackColor = c;
170      stripLine.Text = title;
171      stripLine.Font = new Font("Times New Roman", 12, FontStyle.Bold);
172      stripLine.StripWidth = end - start;
173      stripLine.IntervalOffset = start;
174      this.chart.ChartAreas[0].AxisX.StripLines.Add(stripLine);
175    }
176  }
177}
Note: See TracBrowser for help on using the repository browser.