View on GitHub

VR MARS Strategy

This sample demonstrates a simplified port of the manual trading panel VR---MARS-EN from MQL4 to StockSharp.

The original script provided five predefined lot sizes and buttons to send buy or sell orders. It also displayed multiple labels with trading statistics. In this C# version the visual panel is removed while the core idea of selecting one of the five lot sizes and executing a market order is preserved.

Parameters

  • Lot1 – size of the first lot.
  • Lot2 – size of the second lot.
  • Lot3 – size of the third lot.
  • Lot4 – size of the fourth lot.
  • Lot5 – size of the fifth lot.
  • SelectedLot – number from 1 to 5 specifying which lot size will be used.
  • Buy – when true a market buy order is sent on strategy start.
  • Sell – when true a market sell order is sent on strategy start.

Only one of the direction flags should be enabled at a time. When the strategy starts it activates position protection and sends the corresponding market order using high level helper methods.

Notes

This strategy is intended for educational purposes and does not implement any trading logic beyond immediate order execution.

using System;
using System.Collections.Generic;

using Ecng.Common;

using StockSharp.Algo.Indicators;
using StockSharp.Algo.Strategies;
using StockSharp.BusinessEntities;
using StockSharp.Messages;

namespace StockSharp.Samples.Strategies;

/// <summary>
/// VR MARS strategy using EMA crossover with volume lots.
/// </summary>
public class VRMarsStrategy : Strategy
{
	private readonly StrategyParam<int> _fastPeriod;
	private readonly StrategyParam<int> _slowPeriod;
	private readonly StrategyParam<DataType> _candleType;

	private decimal _prevFast;
	private decimal _prevSlow;
	private bool _hasPrev;

	public int FastPeriod { get => _fastPeriod.Value; set => _fastPeriod.Value = value; }
	public int SlowPeriod { get => _slowPeriod.Value; set => _slowPeriod.Value = value; }
	public DataType CandleType { get => _candleType.Value; set => _candleType.Value = value; }

	public VRMarsStrategy()
	{
		_fastPeriod = Param(nameof(FastPeriod), 5)
			.SetGreaterThanZero()
			.SetDisplay("Fast EMA", "Fast EMA period", "Indicators");
		_slowPeriod = Param(nameof(SlowPeriod), 20)
			.SetGreaterThanZero()
			.SetDisplay("Slow EMA", "Slow EMA period", "Indicators");
		_candleType = Param(nameof(CandleType), TimeSpan.FromHours(4).TimeFrame())
			.SetDisplay("Candle Type", "Type of candles", "General");
	}

	public override IEnumerable<(Security sec, DataType dt)> GetWorkingSecurities()
		=> [(Security, CandleType)];

	protected override void OnReseted()
	{
		base.OnReseted();
		_prevFast = 0; _prevSlow = 0; _hasPrev = false;
	}

	protected override void OnStarted2(DateTime time)
	{
		base.OnStarted2(time);

		var fast = new ExponentialMovingAverage { Length = FastPeriod };
		var slow = new ExponentialMovingAverage { Length = SlowPeriod };

		SubscribeCandles(CandleType).Bind(fast, slow, ProcessCandle).Start();
	}

	private void ProcessCandle(ICandleMessage candle, decimal fast, decimal slow)
	{
		if (candle.State != CandleStates.Finished) return;

		if (!_hasPrev) { _prevFast = fast; _prevSlow = slow; _hasPrev = true; return; }

		if (_prevFast <= _prevSlow && fast > slow)
		{
			if (Position < 0) BuyMarket();
			if (Position <= 0) BuyMarket();
		}
		else if (_prevFast >= _prevSlow && fast < slow)
		{
			if (Position > 0) SellMarket();
			if (Position >= 0) SellMarket();
		}

		_prevFast = fast; _prevSlow = slow;
	}
}