18 using System.Globalization;
52 public static T
Of<T>(
this T second,
IIndicator first,
bool waitForFirstToReady =
true)
55 first.
Updated += (sender, consolidated) =>
58 if (!waitForFirstToReady || first.
IsReady)
60 second.Update(consolidated);
80 var numerator =
new Sum(
"Sum_xy", period);
81 var denominator =
new Sum(
"Sum_y", period);
83 value.Updated += (sender, consolidated) =>
85 x.Update(consolidated);
86 if (x.Samples == y.Samples)
88 numerator.Update(consolidated.Time, consolidated.Value * y.Current.Value);
92 weight.Updated += (sender, consolidated) =>
94 y.Update(consolidated);
95 if (x.Samples == y.Samples)
97 numerator.Update(consolidated.Time, consolidated.Value * x.Current.Value);
99 denominator.Update(consolidated);
102 var resetCompositeIndicator =
new ResetCompositeIndicator(numerator, denominator, GetOverIndicatorComposer(), () =>
108 return resetCompositeIndicator;
123 return left.Plus(constantIndicator);
137 return new(left, right, (l, r) => l.Current.Value + r.Current.Value);
152 return new(name, left, right, (l, r) => l.Current.Value + r.Current.Value);
167 return left.Minus(constantIndicator);
181 return new(left, right, (l, r) => l.Current.Value - r.Current.Value);
196 return new(name, left, right, (l, r) => l.Current.Value - r.Current.Value);
211 return left.Over(constantIndicator);
225 return new(left, right, GetOverIndicatorComposer());
240 return new(name, left, right, GetOverIndicatorComposer());
255 return left.Times(constantIndicator);
269 return new(left, right, (l, r) => l.Current.Value * r.Current.Value);
284 return new(name, left, right, (l, r) => l.Current.Value * r.Current.Value);
309 return new Maximum($
"MAX{period}_Of_{left.Name}", period).Of(left, waitForFirstToReady);
321 return new Minimum($
"MIN{period}_Of_{left.Name}", period).Of(left, waitForFirstToReady);
333 return new SimpleMovingAverage($
"SMA{period}_Of_{left.Name}", period).Of(left, waitForFirstToReady);
348 public static object Of(PyObject second, PyObject first,
bool waitForFirstToReady =
true)
350 dynamic indicator1 = GetIndicatorAsManagedObject(first);
351 dynamic indicator2 = GetIndicatorAsManagedObject(second);
352 return Of(indicator2, indicator1, waitForFirstToReady);
365 dynamic indicator1 = GetIndicatorAsManagedObject(value);
366 dynamic indicator2 = GetIndicatorAsManagedObject(weight);
367 return WeightedBy(indicator1, indicator2, period);
380 dynamic indicator = GetIndicatorAsManagedObject(left);
381 return EMA(indicator, period, smoothingFactor, waitForFirstToReady);
391 public static Maximum MAX(PyObject left,
int period,
bool waitForFirstToReady =
true)
393 dynamic indicator = GetIndicatorAsManagedObject(left);
394 return MAX(indicator, period, waitForFirstToReady);
404 public static Minimum MIN(PyObject left,
int period,
bool waitForFirstToReady =
true)
406 dynamic indicator = GetIndicatorAsManagedObject(left);
407 return MIN(indicator, period, waitForFirstToReady);
419 dynamic indicator = GetIndicatorAsManagedObject(left);
420 return SMA(indicator, period, waitForFirstToReady);
432 public static object Over(PyObject left, decimal constant)
434 dynamic indicatorLeft = GetIndicatorAsManagedObject(left);
435 return Over(indicatorLeft, constant);
448 public static object Over(PyObject left, PyObject right,
string name =
"")
450 dynamic indicatorLeft = GetIndicatorAsManagedObject(left);
451 dynamic indicatorRight = GetIndicatorAsManagedObject(right);
452 if (name.IsNullOrEmpty())
454 return Over(indicatorLeft, indicatorRight);
456 return Over(indicatorLeft, indicatorRight, name);
468 public static object Minus(PyObject left, decimal constant)
470 dynamic indicatorLeft = GetIndicatorAsManagedObject(left);
471 return Minus(indicatorLeft, constant);
484 public static object Minus(PyObject left, PyObject right,
string name =
"")
486 dynamic indicatorLeft = GetIndicatorAsManagedObject(left);
487 dynamic indicatorRight = GetIndicatorAsManagedObject(right);
488 if (name.IsNullOrEmpty())
490 return Minus(indicatorLeft, indicatorRight);
492 return Minus(indicatorLeft, indicatorRight, name);
504 public static object Times(PyObject left, decimal constant)
506 dynamic indicatorLeft = GetIndicatorAsManagedObject(left);
507 return Times(indicatorLeft, constant);
520 public static object Times(PyObject left, PyObject right,
string name =
"")
522 dynamic indicatorLeft = GetIndicatorAsManagedObject(left);
523 dynamic indicatorRight = GetIndicatorAsManagedObject(right);
524 if (name.IsNullOrEmpty())
526 return Times(indicatorLeft, indicatorRight);
528 return Times(indicatorLeft, indicatorRight, name);
540 public static object Plus(PyObject left, decimal constant)
542 dynamic indicatorLeft = GetIndicatorAsManagedObject(left);
543 return Plus(indicatorLeft, constant);
556 public static object Plus(PyObject left, PyObject right,
string name =
"")
558 dynamic indicatorLeft = GetIndicatorAsManagedObject(left);
559 dynamic indicatorRight = GetIndicatorAsManagedObject(right);
560 if (name.IsNullOrEmpty())
562 return Plus(indicatorLeft, indicatorRight);
564 return Plus(indicatorLeft, indicatorRight, name);
567 internal static dynamic GetIndicatorAsManagedObject(
this PyObject indicator)
571 pythonIndicator.SetIndicator(indicator);
572 return pythonIndicator;
575 return indicator.SafeAsManagedObject();
582 private static CompositeIndicator.IndicatorComposer GetOverIndicatorComposer()
584 return (l, r) => r.Current.Value == 0m ?
new IndicatorResult(0m,
IndicatorStatus.MathError) : new IndicatorResult(l.Current.Value / r.Current.Value);