Открыть на GitHub

Стратегия Forex Line

Стратегия Forex Line основана на индикаторе MetaTrader «ForexLine». Для построения быстрой и медленной линий используется двойное сглаживание цены взвешенными скользящими средними. Пересечения этих линий формируют торговые сигналы.

Покупка выполняется, когда быстрая линия пересекает медленную снизу вверх. Продажа выполняется, когда быстрая линия пересекает медленную сверху вниз. Двойное сглаживание помогает отфильтровать рыночный шум.

Детали

  • Условия входа:
    • Лонг: быстрая линия пересекает медленную снизу вверх.
    • Шорт: быстрая линия пересекает медленную сверху вниз.
  • Направление: обе стороны.
  • Условия выхода:
    • Противоположное пересечение закрывает текущую позицию.
  • Стопы: не предусмотрены, можно добавить отдельно.
  • Значения по умолчанию:
    • FastLength1 = 5
    • FastLength2 = 10
    • SlowLength1 = 20
    • SlowLength2 = 20
    • CandleType = таймфрейм 8 часов
  • Фильтры:
    • Категория: следование тренду
    • Направление: обе стороны
    • Индикаторы: взвешенные скользящие средние
    • Стопы: нет
    • Сложность: средняя
    • Таймфрейм: среднесрочный
    • Сезонность: нет
    • Нейронные сети: нет
    • Дивергенции: нет
    • Уровень риска: средний
using System;
using System.Linq;
using System.Collections.Generic;

using Ecng.Common;
using Ecng.Collections;
using Ecng.Serialization;

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

namespace StockSharp.Samples.Strategies;

/// <summary>
/// Forex Line strategy using fast/slow WMA crossover.
/// </summary>
public class ForexLineStrategy : Strategy
{
	private readonly StrategyParam<int> _fastLength;
	private readonly StrategyParam<int> _slowLength;
	private readonly StrategyParam<DataType> _candleType;

	private decimal? _prevFast;
	private decimal? _prevSlow;

	public int FastLength { get => _fastLength.Value; set => _fastLength.Value = value; }
	public int SlowLength { get => _slowLength.Value; set => _slowLength.Value = value; }
	public DataType CandleType { get => _candleType.Value; set => _candleType.Value = value; }

	public ForexLineStrategy()
	{
		_fastLength = Param(nameof(FastLength), 10)
			.SetGreaterThanZero()
			.SetDisplay("Fast WMA Length", "Fast line period", "Parameters");

		_slowLength = Param(nameof(SlowLength), 30)
			.SetGreaterThanZero()
			.SetDisplay("Slow WMA Length", "Slow line period", "Parameters");

		_candleType = Param(nameof(CandleType), TimeSpan.FromHours(4).TimeFrame())
			.SetDisplay("Candle Type", "Type of candles to analyze", "General");
	}

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

	protected override void OnReseted()
	{
		base.OnReseted();
		_prevFast = _prevSlow = null;
	}

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

		var fast = new WeightedMovingAverage { Length = FastLength };
		var slow = new WeightedMovingAverage { Length = SlowLength };

		var subscription = SubscribeCandles(CandleType);
		subscription
			.Bind(fast, slow, ProcessCandle)
			.Start();

		var area = CreateChartArea();
		if (area != null)
		{
			DrawCandles(area, subscription);
			DrawIndicator(area, fast);
			DrawIndicator(area, slow);
			DrawOwnTrades(area);
		}
	}

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

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

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

		_prevFast = fast;
		_prevSlow = slow;
	}
}