Description
UP Trend begins when 2 lines cross DOWN level bottom-up and ends when 2 lines cross UP level top-down
DOWN Trend begins when 2 lines cross UP level top-down and ends when 2 lines cross DOWN level bottom-up
Also indicator shows changes between UP and DOWN trends.
/
#region Using declarations
using System;
using cAlgo.API;
using cAlgo.API.Internals;
using cAlgo.API.Indicators;
using cAlgo.Indicators;
#endregion
namespace cAlgo
{
[Levels(10, 20, 50, 80, 90)]
[Indicator(IsOverlay = false, AutoRescale = true, TimeZone = TimeZones.UTC, AccessRights = AccessRights.None)]
public class SO : Indicator
{
#region Properties
[Parameter("K Periods", DefaultValue = 200)]
public int kPeriods { get; set; }
[Parameter("K Slowing", DefaultValue = 3)]
public int kSlowing { get; set; }
[Parameter("D Periods", DefaultValue = 3)]
public int dPeriods { get; set; }
[Parameter("MA Type", DefaultValue = MovingAverageType.Triangular)]
public MovingAverageType maType { get; set; }
[Parameter("UP Level", DefaultValue = 90, MinValue = 80, MaxValue = 100, Step = 1)]
public int Up_Level { get; set; }
[Parameter("Down Level", DefaultValue = 10, MinValue = 0, MaxValue = 20, Step = 1)]
public int Down_Level { get; set; }
[Output("% D", Color = Colors.Aquamarine, Thickness = 2)]
public IndicatorDataSeries Percent_D { get; set; }
[Output("% K", Color = Colors.Purple, Thickness = 2)]
public IndicatorDataSeries Percent_K { get; set; }
[Output("Trend", Color = Colors.Yellow, Thickness = 1)]
public IndicatorDataSeries Value { get; set; }
#endregion
#region Variables
enum Direction
{
Up,
Down
}
private Direction direction = Direction.Down;
private StochasticOscillator so;
private double Extremum_Value = 0.0;
private int Extremum_Index = 0;
private int Last_Up_Index = 0;
private int Last_Down_Index = 0;
#endregion
protected override void Initialize()
{
so = Indicators.StochasticOscillator(kPeriods, kSlowing, dPeriods, maType);
if (Lines_Are_Lower_Level(Down_Level, 0))
direction = Direction.Up;
if (Lines_Are_Higher_Level(Up_Level, 0))
direction = Direction.Down;
}
public override void Calculate(int index)
{
Percent_K[index] = so.PercentK.LastValue;
Percent_D[index] = so.PercentD.LastValue;
/// Up Level
if (Lines_Just_Crossed_From_Up_To_Down_Level(Up_Level, index))
{
if (direction == Direction.Up)
{
direction = Direction.Down;
Last_Up_Index = index;
Set_Extremum_At(index, Up_Level);
}
if (direction == Direction.Down && Extremum_Value == Up_Level)
{
Last_Up_Index = index;
Move_Extremum_At(index, Up_Level);
}
}
/// Down Level
if (Lines_Just_Crossed_From_Down_To_Up_Level(Down_Level, index))
{
if (direction == Direction.Down)
{
direction = Direction.Up;
Last_Down_Index = index;
Set_Extremum_At(index, Down_Level);
}
if (direction == Direction.Up && Extremum_Value == Down_Level)
{
Last_Down_Index = index;
Move_Extremum_At(index, Down_Level);
}
}
if (index - 1 != Extremum_Index)
{
Value[index - 1] = Double.NaN;
Value[index] = Percent_D[index];
}
}
private bool Lines_Are_Lower_Level(double level, int index)
{
return Percent_K[index] < level && Percent_D[index] < level;
}
private bool Lines_Are_Higher_Level(double level, int index)
{
return Percent_K[index] > level && Percent_D[index] > level;
}
private bool Lines_Just_Crossed_From_Up_To_Down_Level(double level, int index)
{
return Lines_Are_Lower_Level(level, index) && (Percent_K[index - 1] >= level || Percent_D[index - 1] >= level);
}
private bool Lines_Just_Crossed_From_Down_To_Up_Level(double level, int index)
{
return Lines_Are_Higher_Level(level, index) && (Percent_K[index - 1] <= level || Percent_D[index - 1] <= level);
}
private void Move_Extremum_At(int index, double v)
{
Value[Extremum_Index] = Double.NaN;
ChartObjects.RemoveObject("Info " + Extremum_Index);
Set_Extremum_At(index, v);
}
private void Set_Extremum_At(int Index, double V)
{
Extremum_Index = Index;
Extremum_Value = V;
Value[Extremum_Index] = Extremum_Value;
VerticalAlignment Point_VA = VerticalAlignment.Center;
HorizontalAlignment Point_HA = HorizontalAlignment.Center;
Colors Point_Color = Colors.Yellow;
ChartObjects.DrawText("Direction " + Index, "•", Index, V, Point_VA, Point_HA, Point_Color);
double Low = MarketSeries.Low[Last_Down_Index];
double High = MarketSeries.High[Last_Up_Index];
double Trend_Value = (High - Low) / Symbol.TickSize;
string Dir = direction == Direction.Down ? "▲" : "▼";
string Info = Dir + " " + Trend_Value.ToString("N0");
VerticalAlignment Text_VA = VerticalAlignment.Center;
HorizontalAlignment Text_HA = HorizontalAlignment.Center;
Colors Text_Color = Colors.Yellow;
ChartObjects.DrawText("Info " + Index, Info, Index, V >= 50 ? V - 10 : V + 10, Text_VA, Text_HA, Text_Color);
}
}
}
diiptrade
Joined on 17.11.2016
- Distribution: Free
- Language: C#
- Trading platform: cTrader Automate
- File name: SO.algo
- Rating: 5
- Installs: 6488
- Modified: 13/10/2021 09:54
Comments
// This has been modified, to be more easily understandable.
using System;
using cAlgo.API;
using cAlgo.API.Internals;
using cAlgo.API.Indicators;
using cAlgo.Indicators;
namespace cAlgo
{
[Levels(10, 20, 50, 80, 90)]
[Indicator(IsOverlay = false, AutoRescale = true, AccessRights = AccessRights.None)]
public class SO : Indicator
{
[Parameter("K Periods", DefaultValue = 200)]
public int kPeriods { get; set; }
[Parameter("K Slowing", DefaultValue = 3)]
public int kSlowing { get; set; }
[Parameter("D Periods", DefaultValue = 3)]
public int dPeriods { get; set; }
[Parameter("MA Type", DefaultValue = MovingAverageType.Triangular)]
public MovingAverageType maType { get; set; }
[Parameter("UP Level", DefaultValue = 90, MinValue = 80, MaxValue = 100, Step = 1)]
public int Up_Level { get; set; }
[Parameter("Down Level", DefaultValue = 10, MinValue = 0, MaxValue = 20, Step = 1)]
public int Down_Level { get; set; }
[Output("% D", Color = Colors.Aquamarine, Thickness = 2)]
public IndicatorDataSeries Percent_D { get; set; }
[Output("% K", Color = Colors.Purple, Thickness = 2)]
public IndicatorDataSeries Percent_K { get; set; }
[Output("Trend", Color = Colors.Yellow, Thickness = 1)]
public IndicatorDataSeries Value { get; set; }
private StochasticOscillator so;
private double Extremum_Value = 0.0;
private int Extremum_Index = 0;
private int Last_Up_Index = 0;
private int Last_Down_Index = 0;
private int direction = 0;
protected override void Initialize()
{
so = Indicators.StochasticOscillator(kPeriods, kSlowing, dPeriods, maType);
}
public override void Calculate(int index)
{
Percent_K[index] = so.PercentK[index];
Percent_D[index] = so.PercentD[index];
//---------- K value is Stockastic value ( purple) , D is MA3 of it.
//----------- if ( K is now < 90% and D < 90% ) and (the previous K >= 90% or the Previous D is >= 90%)
//----------- this is to get the position for the dot.
//UP LEVEL
if ((Percent_K[index] < Up_Level && Percent_D[index] < Up_Level) && (Percent_K[index - 1] >= Up_Level || Percent_D[index - 1] >= Up_Level))
{
if (direction == 1)
{
direction = 0;
Last_Up_Index = index;
Extremum_Index = index;
Extremum_Value = Up_Level;
Value[Extremum_Index] = Extremum_Value;
ChartObjects.DrawText("Direction " + index, "•", index, Up_Level, VerticalAlignment.Center, HorizontalAlignment.Center, Colors.Yellow);
double Low = MarketSeries.Low[Last_Down_Index];
double High = MarketSeries.High[Last_Up_Index];
double Trend_Value = (High - Low) / Symbol.TickSize;
string Dir = direction == 0 ? "▲" : "▼";
string Info = Dir + " " + Trend_Value.ToString("N0");
ChartObjects.DrawText("Info " + index, Info, index, Up_Level >= 50 ? Up_Level - 10 : Up_Level + 10, VerticalAlignment.Center, HorizontalAlignment.Center, Colors.Yellow);
}
if (direction == 0 && Extremum_Value == Up_Level)
{
Last_Up_Index = index;
Value[Extremum_Index] = Double.NaN;
ChartObjects.RemoveObject("Info " + Extremum_Index);
Extremum_Index = index;
Extremum_Value = Up_Level;
Value[Extremum_Index] = Extremum_Value;
ChartObjects.DrawText("Direction " + index, "•", index, Up_Level, VerticalAlignment.Center, HorizontalAlignment.Center, Colors.Yellow);
double Low = MarketSeries.Low[Last_Down_Index];
double High = MarketSeries.High[Last_Up_Index];
double Trend_Value = (High - Low) / Symbol.TickSize;
string Dir = direction == 0 ? "▲" : "▼";
string Info = Dir + " " + Trend_Value.ToString("N0");
ChartObjects.DrawText("Info " + index, Info, index, Up_Level >= 50 ? Up_Level - 10 : Up_Level + 10, VerticalAlignment.Center, HorizontalAlignment.Center, Colors.Yellow);
}
}
//---------------------------------------------------------------------------------
/// Down Level
if ((Percent_K[index] > Down_Level && Percent_D[index] > Down_Level) && (Percent_K[index - 1] <= Down_Level || Percent_D[index - 1] <= Down_Level))
{
if (direction == 0)
{
direction = 1;
Last_Down_Index = index;
Extremum_Index = index;
Extremum_Value = Down_Level;
Value[Extremum_Index] = Extremum_Value;
ChartObjects.DrawText("Direction " + index, "•", index, Down_Level, VerticalAlignment.Center, HorizontalAlignment.Center, Colors.Yellow);
double Low = MarketSeries.Low[Last_Down_Index];
double High = MarketSeries.High[Last_Up_Index];
double Trend_Value = (High - Low) / Symbol.TickSize;
string Dir = direction == 0 ? "▲" : "▼";
string Info = Dir + " " + Trend_Value.ToString("N0");
ChartObjects.DrawText("Info " + index, Info, index, Down_Level >= 50 ? Down_Level - 10 : Down_Level + 10, VerticalAlignment.Center, HorizontalAlignment.Center, Colors.Yellow);
}
if (direction == 1 && Extremum_Value == Down_Level)
{
Last_Down_Index = index;
Value[Extremum_Index] = Double.NaN;
ChartObjects.RemoveObject("Info " + Extremum_Index);
Extremum_Index = index;
Extremum_Value = Down_Level;
Value[Extremum_Index] = Extremum_Value;
ChartObjects.DrawText("Direction " + index, "•", index, Down_Level, VerticalAlignment.Center, HorizontalAlignment.Center, Colors.Yellow);
double Low = MarketSeries.Low[Last_Down_Index];
double High = MarketSeries.High[Last_Up_Index];
double Trend_Value = (High - Low) / Symbol.TickSize;
string Dir = direction == 0 ? "▲" : "▼";
string Info = Dir + " " + Trend_Value.ToString("N0");
ChartObjects.DrawText("Info " + index, Info, index, Down_Level >= 50 ? Down_Level - 10 : Down_Level + 10, VerticalAlignment.Center, HorizontalAlignment.Center, Colors.Yellow);
}
}
if (index - 1 != Extremum_Index)
{
Value[index - 1] = Double.NaN;
Value[index] = Percent_D[index];
}
}
}
}
That's a good one, my comrade!
// This Just puts an Icon above the price, on the chart.
using System;
using cAlgo.API;
using cAlgo.API.Internals;
using cAlgo.API.Indicators;
using cAlgo.Indicators;
// AutoRescale = true
namespace cAlgo
{
[Indicator(IsOverlay = true, AccessRights = AccessRights.None)]
public class SO : Indicator
{
[Parameter("K Periods", DefaultValue = 200)]
public int kPeriods { get; set; }
[Parameter("K Slowing", DefaultValue = 3)]
public int kSlowing { get; set; }
[Parameter("D Periods", DefaultValue = 3)]
public int dPeriods { get; set; }
[Parameter("MA Type", DefaultValue = MovingAverageType.Triangular)]
public MovingAverageType maType { get; set; }
[Parameter("UP Level", DefaultValue = 90, MinValue = 80, MaxValue = 100, Step = 1)]
public int Up_Level { get; set; }
[Parameter("Down Level", DefaultValue = 10, MinValue = 0, MaxValue = 20, Step = 1)]
public int Down_Level { get; set; }
private StochasticOscillator so;
private double Extremum_Value = 0.0;
private int Extremum_Index = 0;
private int Last_Up_Index = 0;
private int Last_Down_Index = 0;
private int direction = 0;
protected override void Initialize()
{
so = Indicators.StochasticOscillator(kPeriods, kSlowing, dPeriods, maType);
}
public override void Calculate(int index)
{
//---------- K value is Stockastic value ( purple) , D is MA3 of it.
//----------- if ( K is now < 90% and the previous K >= 90% )
//----------- this is our setup for upper entry
//UP LEVEL
if (so.PercentK[index] < Up_Level && so.PercentK[index - 1] >= Up_Level)
{
var high = MarketSeries.High[index];
var highPlus2Pip = high + (5 * Symbol.PipSize);
ChartObjects.DrawText("Info " + index, "▼", index, highPlus2Pip, VerticalAlignment.Center, HorizontalAlignment.Center, Colors.White);
}
//DOWN lEVEL
if (so.PercentK[index] > Down_Level && so.PercentK[index - 1] <= Down_Level)
{
var low = MarketSeries.Low[index];
var lowPlus2Pip = low - (5 * Symbol.PipSize);
ChartObjects.DrawText("Info " + index, "▲", index, lowPlus2Pip, VerticalAlignment.Center, HorizontalAlignment.Center, Colors.White);
}
}
}
}