Auf GitHub ansehen

Maximus vX Lite-Strategie

Diese Strategie versucht, Ausbrüche aus kurzfristigen Konsolidierungszonen zu handeln. Sie sucht nach kompakten Preisbereichen im 15-Minuten-Chart und eröffnet Trades, wenn der Preis diese Bereiche um eine bestimmte Distanz verlässt.

Strategielogik

  1. Für jede abgeschlossene 15-Minuten-Kerze werden das höchste Hoch und das niedrigste Tief der letzten 40 Kerzen berechnet.
  2. Wenn der Abstand zwischen diesen Extremen unter dem Parameter Range liegt, wird eine Konsolidierungszone angenommen.
  3. Nach Ablauf der Delay Open-Periode ohne neue Trades löst ein Ausbruch über die obere Grenze plus Distance Punkte eine Long-Position aus, während ein Ausbruch unter die untere Grenze minus Distance Punkte eine Short-Position auslöst.
  4. Ein fester Stop Loss und ein Trailing-Stop von Trail Punkten werden angewandt, sobald eine Position eröffnet wird.
  5. Konsolidierungsgrenzen werden nach Ablauf der Period-Stunden zurückgesetzt.

Parameter

  • DelayOpen – Stunden Wartezeit vor der Eröffnung eines neuen Trades.
  • Distance – Ausbruchsdistanz von der Konsolidierungsgrenze in Punkten.
  • Period – Stunden, nach denen Konsolidierungsniveaus neu berechnet werden.
  • Range – Maximale Größe der Konsolidierungszone in Punkten.
  • StopLoss – Anfänglicher Stop-Loss in Punkten.
  • Trail – Trailing-Stop-Distanz in Punkten.

Hinweise

Die Strategie verwendet ausschließlich die High-Level-API: Kerzen werden über SubscribeCandles empfangen, und Indikatorwerte werden mit Bind gebunden. Orders werden mit den Methoden BuyMarket und SellMarket gesendet. Kommentare im Quellcode sind auf Englisch verfasst.

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>
/// Breakout strategy based on consolidation zones.
/// </summary>
public class MaximusVxLiteStrategy : Strategy
{
	private readonly StrategyParam<int> _lookback;
	private readonly StrategyParam<DataType> _candleType;

	private decimal _prevHigh;
	private decimal _prevLow;
	private bool _hasPrev;

	public int Lookback { get => _lookback.Value; set => _lookback.Value = value; }
	public DataType CandleType { get => _candleType.Value; set => _candleType.Value = value; }

	public MaximusVxLiteStrategy()
	{
		_lookback = Param(nameof(Lookback), 20)
			.SetDisplay("Lookback", "Highest/Lowest lookback period", "General");

		_candleType = Param(nameof(CandleType), TimeSpan.FromHours(4).TimeFrame())
			.SetDisplay("Candle Type", "Time frame for candles", "General");
	}

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

	protected override void OnReseted()
	{
		base.OnReseted();
		_prevHigh = 0;
		_prevLow = 0;
		_hasPrev = false;
	}

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

		var highest = new Highest { Length = Lookback };
		var lowest = new Lowest { Length = Lookback };

		SubscribeCandles(CandleType).Bind(highest, lowest, ProcessCandle).Start();
	}

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

		if (!_hasPrev)
		{
			_prevHigh = highest;
			_prevLow = lowest;
			_hasPrev = true;
			return;
		}

		var close = candle.ClosePrice;

		// Breakout above previous highest
		if (close > _prevHigh && Position <= 0)
		{
			if (Position < 0) BuyMarket();
			BuyMarket();
		}
		// Breakout below previous lowest
		else if (close < _prevLow && Position >= 0)
		{
			if (Position > 0) SellMarket();
			SellMarket();
		}

		_prevHigh = highest;
		_prevLow = lowest;
	}
}