Lean  $LEAN_TAG$
Vortex.cs
1 /*
2  * QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
3  * Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14 */
15 
16 using System;
18 
20 {
21  /// <summary>
22  /// Represents the Vortex Indicator, which identifies the start and continuation of market trends.
23  /// It includes components that capture positive (upward) and negative (downward) trend movements.
24  /// This indicator compares the ranges within the current period to previous periods to calculate
25  /// upward and downward movement trends.
26  /// </summary>
28  {
29  private readonly int _period;
30  private readonly AverageTrueRange _atr;
31  private readonly Sum _atrSum;
32  private readonly Sum _plusVMSum;
33  private readonly Sum _minusVMSum;
34  private IBaseDataBar _previousInput;
35 
36  /// <summary>
37  /// Gets the Positive Vortex Indicator, which reflects positive trend movements.
38  /// </summary>
39  public IndicatorBase<IndicatorDataPoint> PlusVortex { get; private set; }
40 
41  /// <summary>
42  /// Gets the Negative Vortex Indicator, which reflects negative trend movements.
43  /// </summary>
44  public IndicatorBase<IndicatorDataPoint> MinusVortex { get; private set; }
45 
46  /// <summary>
47  /// Indicates whether this indicator is fully ready and all buffers have been filled.
48  /// </summary>
49  public override bool IsReady => Samples >= _period;
50 
51  /// <summary>
52  /// The minimum number of samples needed for the indicator to be ready and provide reliable values.
53  /// </summary>
54  public int WarmUpPeriod => _period;
55 
56  /// <summary>
57  /// Initializes a new instance of the <see cref="Vortex"/> class using the specified period.
58  /// </summary>
59  /// <param name="period">The number of periods used to construct the Vortex Indicator.</param>
60  public Vortex(int period)
61  : this($"VTX({period})", period)
62  {
63  }
64 
65  /// <summary>
66  /// Initializes a new instance of the <see cref="Vortex"/> class with a custom name and period.
67  /// </summary>
68  /// <param name="name">The custom name for this instance of the Vortex Indicator.</param>
69  /// <param name="period">The number of periods used to construct the Vortex Indicator.</param>
70  public Vortex(string name, int period)
71  : base(name)
72  {
73  _period = period;
74  _atr = new AverageTrueRange($"{Name}_ATR", 1, MovingAverageType.Simple);
75  _atrSum = new Sum("ATR_Sum", period).Of(_atr);
76  _plusVMSum = new Sum("PlusVM_Sum", period);
77  _minusVMSum = new Sum("MinusVM_Sum", period);
78 
79  PlusVortex = _plusVMSum.Over(_atrSum);
80  MinusVortex = _minusVMSum.Over(_atrSum);
81  }
82 
83  /// <summary>
84  /// Computes the next value of the Vortex Indicator based on the provided input.
85  /// </summary>
86  /// <param name="input">The input data used to compute the indicator value.</param>
87  /// <returns>The computed value of the indicator.</returns>
88  protected override decimal ComputeNextValue(IBaseDataBar input)
89  {
90  _atr.Update(input);
91 
92  if (_previousInput != null)
93  {
94  var plusVMValue = Math.Abs(input.High - _previousInput.Low);
95  var minusVMValue = Math.Abs(input.Low - _previousInput.High);
96 
97  _plusVMSum.Update(input.Time, plusVMValue);
98  _minusVMSum.Update(input.Time, minusVMValue);
99  }
100 
101  _previousInput = input;
102 
103  if (!IsReady)
104  {
105  return 0;
106  }
107 
108  return (PlusVortex.Current.Value + MinusVortex.Current.Value) / 2;
109  }
110 
111  /// <summary>
112  /// Resets all indicators and internal state.
113  /// </summary>
114  public override void Reset()
115  {
116  base.Reset();
117  _atr.Reset();
118  _atrSum.Reset();
119  _plusVMSum.Reset();
120  _minusVMSum.Reset();
121  PlusVortex.Reset();
122  MinusVortex.Reset();
123  _previousInput = null;
124  }
125  }
126 }