Bar close above SMA not working
Bar close above SMA not working
22 Sep 2021, 13:32
Hi,
I am trying to get some code working. I want an if function to work when the last close price for the bar is higher than a SMA.
It just isnt working for me, any pointers ??
protected override void OnBar()
{
var smavalue = _sma2.Result.Last(1);
var close1 = MarketSeries.Close.Last(1);
private void ManagePositions()
{
if (stoch.PercentK.LastValue < lowest)
{
if (close1 > smavalue) !@!!! this line here
{
{
EngulfBear();
}
}
}
/// This is all the close conditions
if (stoch.PercentK.LastValue >= highest)
{
ClosePosition(TradeType.Buy);
}
foreach (var position in Positions.FindAll(InstanceName, Symbol))
{
if (position.GrossProfit > TPSimple)
ClosePosition(position);
}
}
Replies
alfonsotradingco
24 Sep 2021, 12:24
RE:
amusleh said:
Hi,
Your code syntax is invalid, please post full code of your cBot then we will be able to help you.
Please check the simple moving average API reference examples: cAlgo API Reference - SimpleMovingAverage Interface (ctrader.com)
Hey sorry, here it is
using System;
using System.Linq;
using cAlgo.API;
using cAlgo.API.Indicators;
using cAlgo.API.Internals;
using cAlgo.Indicators;
/*
* POPULAR SIMPLE MOVING AVERAGES
*
* The simple moving average (SMA) is the most basic of the moving averages used for trading.
* The simple moving average formula is calculated by taking the average closing price of a stock over the last "x" periods.
*
* 5 - SMA - For the hyper trader. This short of an SMA will constantly give you signals. The best use of a 5-SMA is as a trade trigger in conjunction with a longer SMA period.
* 10 - SMA - popular with the short-term traders. Great swing traders and day traders.
* 20 - SMA - the last stop on the bus for short-term traders. Beyond 20-SMA you are basically looking at primary trends.
* 50 - SMA - use the trader to gauge mid-term trends.
* 200 -SMA - welcome to the world of long-term trend followers. Most investors will look for a cross above or below this average to represent if the stock is in a bullish or bearish trend.
*
* Modifications
* =============
* 02.12.2017 - Added trailing stop - phayes
* 03.12.2017 - Added a Break-even - phayes
*/
namespace cAlgo
{
[Robot(TimeZone = TimeZones.UTC, AccessRights = AccessRights.None)]
public class SMAandStoch : Robot
{
private double SLsimple;
#region User defined parameters
[Parameter("Instance Name", DefaultValue = "001")]
public string InstanceName { get; set; }
[Parameter("Lot Size", DefaultValue = 0.1)]
public double LotSize { get; set; }
[Parameter("Source SMA ")]
public DataSeries SourceSma2 { get; set; }
[Parameter("Slow SMA", DefaultValue = 200, MinValue = 150, MaxValue = 250)]
public int PeriodsSma2 { get; set; }
[Parameter("Calculate OnBar", DefaultValue = true)]
public bool CalculateOnBar { get; set; }
[Parameter("Include Trailing Stop", DefaultValue = true)]
public bool IncludeTrailingStop { get; set; }
[Parameter("Trailing Stop Trigger (pips)", DefaultValue = 20)]
public int TrailingStopTrigger { get; set; }
[Parameter("Trailing Stop Step (pips)", DefaultValue = 10)]
public int TrailingStopStep { get; set; }
[Parameter("High Stoch Level", DefaultValue = 65)]
public int highest { get; set; }
[Parameter("Low Stock Level", DefaultValue = 30)]
public int lowest { get; set; }
[Parameter("Stop Loss (pips)", DefaultValue = 100)]
public int StopLoss { get; set; }
[Parameter("Take Profit (pips)", DefaultValue = 100)]
public int TakeProfit { get; set; }
[Parameter("Trigger (pips)", DefaultValue = 10)]
public int Trigger { get; set; }
[Parameter("MinBalance", DefaultValue = 500)]
public double MinBalance { get; set; }
[Parameter("Take Profit Simple", DefaultValue = 100)]
public double TPSimple { get; set; }
[Parameter("Stop Loss Simple", DefaultValue = -10)]
public double SLSimple { get; set; }
[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("Look Back Period ", DefaultValue = 100)]
public int lookback { get; set; }
[Parameter("Use Bullish Engulfing ? ", DefaultValue = true)]
public bool useBU { get; set; }
[Parameter("Use Bearish Engulfing ? ", DefaultValue = true)]
public bool useBE { get; set; }
#endregion
#region Indicator declarations
private SimpleMovingAverage _sma2 { get; set; }
private StochasticOscillator stoch { get; set; }
#endregion
#region cTrader events
/// <summary>
/// This is called when the robot first starts, it is only called once.
/// </summary>
protected override void OnStart()
{
// construct the indicators
_sma2 = Indicators.SimpleMovingAverage(SourceSma2, PeriodsSma2);
stoch = Indicators.StochasticOscillator(kPeriods, kSlowing, dPeriods, maType);
}
/// <summary>
/// This method is called every time the price changes for the symbol
/// </summary>
protected override void OnTick()
{
var close4 = MarketSeries.Close.Last(1);
if (CalculateOnBar)
{
return;
}
ManagePositions();
if (IncludeTrailingStop)
{
SetTrailingStop();
}
CloseTP();
var positionTP = Positions.Find(InstanceName, Symbol, TradeType.Buy);
if (positionTP != null && positionTP.GrossProfit > TPSimple)
{
ClosePosition(positionTP);
}
var positionSL = Positions.Find(InstanceName, Symbol, TradeType.Buy);
if (positionSL != null && positionTP.GrossProfit < SLSimple)
{
ClosePosition(positionTP);
}
}
/*
var positionSL = Positions.Find(InstanceName, Symbol, TradeType.Buy);
var stopLoss = positionSL.EntryPrice - SLSimple * Symbol.PipSize;
if (positionSL != null && StopLoss < close4)
{
Print("Position SL price is {0}", positionSL.StopLoss);
ClosePosition(positionSL);
}
*/
/// <summary>
/// This method is called at every candle (bar) close, when it has formed
/// </summary>
protected override void OnBar()
{
var smavalue = _sma2.Result.Last(1);
var close1 = MarketSeries.Close.Last(1);
var close2 = MarketSeries.Close.Last(2);
var close3 = MarketSeries.Close.Last(3);
if (!CalculateOnBar)
{
return;
}
Print("Last Candle close price was: {0}, SMA Slow value was: {1}", close1, smavalue);
ManagePositions();
}
/// <summary>
/// This method is called when your robot stops, can be used to clean-up memory resources.
/// </summary>
protected override void OnStop()
{
// unused
}
#endregion
#region Position management
private void ManagePositions()
{
if (stoch.PercentK.LastValue < lowest)
{
if (close1 > smavalue)
{
{
EngulfBear();
}
}
}
/// This is all the close conditions
if (stoch.PercentK.LastValue >= highest)
{
ClosePosition(TradeType.Buy);
}
foreach (var position in Positions.FindAll(InstanceName, Symbol))
{
if (position.GrossProfit > TPSimple)
ClosePosition(position);
}
}
/// <summary>
/// Opens a new long position
/// </summary>
/// <param name="type"></param>
private void OpenPosition(TradeType type)
{
// calculate volume from lot size.
long volume = Symbol.QuantityToVolume(LotSize);
// open a new position
ExecuteMarketOrder(type, this.Symbol, volume, InstanceName, null, null);
}
/// <summary>
///
/// </summary>
/// <param name="type"></param>
private void ClosePosition(TradeType type)
{
var p = Positions.Find(InstanceName, this.Symbol, type);
if (p != null)
{
ClosePosition(p);
}
}
#endregion
#region Candle Patterns
private void EngulfBear()
{
if (!useBE)
return;
for (var i = 1; i <= lookback; i++)
{
var c = MarketSeries.Close.Last(i);
var o = MarketSeries.Open.Last(i);
var h = MarketSeries.High.Last(i);
var l = MarketSeries.Low.Last(i);
var ct = MarketSeries.Close.Last(i + 1);
var ot = MarketSeries.Open.Last(i + 1);
var ht = MarketSeries.High.Last(i + 1);
var lt = MarketSeries.Low.Last(i + 1);
if (ct < ot || c > o)
continue;
if (c < ot)
{
// if there is no buy position open, open one and close any sell position that is open
if (!IsPositionOpenByType(TradeType.Buy))
{
OpenPosition(TradeType.Buy);
}
ClosePosition(TradeType.Sell);
}
}
}
#endregion
#region Position Information
/// <summary>
///
/// </summary>
/// <param name="type"></param>
/// <returns></returns>
private bool IsPositionOpenByType(TradeType type)
{
var p = Positions.FindAll(InstanceName, Symbol, type);
if (p.Count() >= 1)
{
return true;
}
return false;
}
#endregion
#region Trailing Stop
/// <summary>
/// When the profit in pips is above or equal to Trigger the stop loss will start trailing the spot price.
/// TrailingStop defines the number of pips the Stop Loss trails the spot price by.
/// If Trigger is 0 trailing will begin immediately.
/// </summary>
private void SetTrailingStop()
{
var sellPositions = Positions.FindAll(InstanceName, Symbol, TradeType.Sell);
foreach (Position position in sellPositions)
{
double distance = position.EntryPrice - Symbol.Ask;
if (distance < TrailingStopTrigger * Symbol.PipSize)
continue;
double newStopLossPrice = Symbol.Ask + TrailingStopStep * Symbol.PipSize;
if (position.StopLoss == null || newStopLossPrice < position.StopLoss)
{
ModifyPosition(position, newStopLossPrice, position.TakeProfit);
}
}
var buyPositions = Positions.FindAll(InstanceName, Symbol, TradeType.Buy);
foreach (Position position in buyPositions)
{
double distance = Symbol.Bid - position.EntryPrice;
if (distance < TrailingStopTrigger * Symbol.PipSize)
continue;
double newStopLossPrice = Symbol.Bid - TrailingStopStep * Symbol.PipSize;
if (position.StopLoss == null || newStopLossPrice > position.StopLoss)
{
ModifyPosition(position, newStopLossPrice, position.TakeProfit);
}
}
}
#endregion
#region Stops and Take Profits (I.L)
private void CloseTP()
{
foreach (var position in Positions.FindAll(InstanceName, Symbol))
{
if (position.GrossProfit > TPSimple)
ClosePosition(position);
}
return;
}
private void CloseSL()
{
foreach (var position in Positions.FindAll(InstanceName, Symbol))
{
if (position.GrossProfit * -1 < SLsimple)
ClosePosition(position);
}
return;
}
#endregion
}
}
@alfonsotradingco
amusleh
24 Sep 2021, 16:00
Hi,
I still can't compile your source code as it has lots of errors.
You can use the below sample cBot as a guide on how to use SMA with close prices:
using cAlgo.API;
using cAlgo.API.Indicators;
namespace cAlgo.Robots
{
// This sample cBot shows how to use the Simple Moving Average indicator
[Robot(TimeZone = TimeZones.UTC, AccessRights = AccessRights.None)]
public class SimpleMovingAverageSample : Robot
{
private double _volumeInUnits;
private SimpleMovingAverage _sma;
[Parameter("Source", Group = "MA")]
public DataSeries MaSource { get; set; }
[Parameter("Period", DefaultValue = 9, Group = "MA")]
public int MaPeriod { get; set; }
[Parameter("Volume (Lots)", DefaultValue = 0.01, Group = "Trade")]
public double VolumeInLots { get; set; }
[Parameter("Stop Loss (Pips)", DefaultValue = 10, Group = "Trade")]
public double StopLossInPips { get; set; }
[Parameter("Take Profit (Pips)", DefaultValue = 10, Group = "Trade")]
public double TakeProfitInPips { get; set; }
[Parameter("Label", DefaultValue = "Sample", Group = "Trade")]
public string Label { get; set; }
public Position[] BotPositions
{
get
{
return Positions.FindAll(Label);
}
}
protected override void OnStart()
{
_volumeInUnits = Symbol.QuantityToVolumeInUnits(VolumeInLots);
_sma = Indicators.SimpleMovingAverage(MaSource, MaPeriod);
}
protected override void OnBar()
{
if (_sma.Result.HasCrossedAbove(Bars.ClosePrices, 0))
{
ClosePositions(TradeType.Sell);
ExecuteMarketOrder(TradeType.Buy, SymbolName, _volumeInUnits, Label, StopLossInPips, TakeProfitInPips);
}
else if (_sma.Result.HasCrossedBelow(Bars.ClosePrices, 0))
{
ClosePositions(TradeType.Buy);
ExecuteMarketOrder(TradeType.Sell, SymbolName, _volumeInUnits, Label, StopLossInPips, TakeProfitInPips);
}
}
private void ClosePositions(TradeType tradeType)
{
foreach (var position in BotPositions)
{
if (position.TradeType != tradeType) continue;
ClosePosition(position);
}
}
}
}
@amusleh
amusleh
22 Sep 2021, 13:53 ( Updated at: 22 Sep 2021, 13:54 )
Hi,
Your code syntax is invalid, please post full code of your cBot then we will be able to help you.
Please check the simple moving average API reference examples: cAlgo API Reference - SimpleMovingAverage Interface (ctrader.com)
@amusleh