Swetten is a neural-network driven breakout strategy that was originally distributed for MetaTrader 4. It evaluates the spread between a long-term 233-period simple moving average and ten faster moving averages calculated on one-minute candles. The spreads are fed into a radial basis network that produces a bullish or bearish activation level. When the activation is positive the strategy enters long, when it is negative it enters short.
Market & Timeframe
Designed for major FX pairs (the original code targeted EURUSD).
Analysis uses one-minute candles and decisions are made only on completed candles.
Signals are evaluated every two hours at the top of the hour (00:00, 02:00, …, 22:00 exchange time). No trades are opened on Saturdays or Sundays.
Neural network inputs are the differences between the 233-period average and each faster average.
Before passing to the network the inputs are clamped to trained ranges, normalized, and scaled with the same coefficients used in the original DLL.
The radial basis network is replicated exactly from the exported EURUSDn function, consisting of 38 Gaussian features whose outputs are averaged to obtain the final activation.
Trading Rules
Wait for the close of a one-minute candle that ends on an even hour and falls on a weekday.
Compute the neural network activation from the moving-average spreads.
If activation > 0 and the current position is not long, send a market buy for TradeVolume + abs(current position) lots.
If activation < 0 and the current position is not short, send a market sell for TradeVolume + abs(current position) lots.
Positions are protected by:
A fixed take profit defined in price steps (TakeProfitPoints).
A fixed stop loss defined in price steps (StopLossPoints).
When either level is touched using candle high/low extremes, the position is closed by a market order.
Parameters
Name
Description
Default
CandleType
Candle series used for calculations.
1-minute time frame
TradeVolume
Base order volume in lots.
0.1
SlowPeriod
Period of the baseline simple moving average.
233
TakeProfitPoints
Profit target distance in price steps.
150
StopLossPoints
Stop-loss distance in price steps.
40
Conversion Notes
The DLL-based neural network from MetaTrader was fully ported to C# by translating the exported function to managed code.
Protective exits mimic the original OrderClose conditions by checking candle highs and lows against price step thresholds.
Entry management keeps track of the latest fill price via OnNewMyTrade to align exits with actual fills.
All comments were rewritten in English and the code uses high-level StockSharp APIs (SubscribeCandles, Bind) as required by the conversion guidelines.
using System;
using Ecng.Common;
using StockSharp.Algo.Indicators;
using StockSharp.Algo.Strategies;
using StockSharp.BusinessEntities;
using StockSharp.Messages;
namespace StockSharp.Samples.Strategies;
/// <summary>
/// Swetten strategy: multi-SMA spread crossover system.
/// Uses fast SMA (5) and slow SMA (50) to generate trend signals.
/// Buys when fast crosses above slow, sells when fast crosses below slow.
/// </summary>
public class SwettenStrategy : Strategy
{
private readonly StrategyParam<DataType> _candleType;
private readonly StrategyParam<int> _fastPeriod;
private readonly StrategyParam<int> _slowPeriod;
private decimal _prevFast;
private decimal _prevSlow;
private bool _isReady;
public DataType CandleType
{
get => _candleType.Value;
set => _candleType.Value = value;
}
public int FastPeriod
{
get => _fastPeriod.Value;
set => _fastPeriod.Value = value;
}
public int SlowPeriod
{
get => _slowPeriod.Value;
set => _slowPeriod.Value = value;
}
public SwettenStrategy()
{
_candleType = Param(nameof(CandleType), TimeSpan.FromMinutes(5).TimeFrame())
.SetDisplay("Candle Type", "Candle type for strategy", "General");
_fastPeriod = Param(nameof(FastPeriod), 8)
.SetDisplay("Fast SMA", "Fast SMA period", "Indicators");
_slowPeriod = Param(nameof(SlowPeriod), 34)
.SetDisplay("Slow SMA", "Slow SMA period", "Indicators");
}
/// <inheritdoc />
/// <inheritdoc />
protected override void OnReseted()
{
base.OnReseted();
_prevFast = 0;
_prevSlow = 0;
_isReady = false;
}
protected override void OnStarted2(DateTime time)
{
base.OnStarted2(time);
_prevFast = 0;
_prevSlow = 0;
_isReady = false;
var fast = new SMA { Length = FastPeriod };
var slow = new SMA { Length = SlowPeriod };
var subscription = SubscribeCandles(CandleType);
subscription
.Bind(fast, slow, OnProcess)
.Start();
var area = CreateChartArea();
if (area != null)
{
DrawCandles(area, subscription);
DrawIndicator(area, fast);
DrawIndicator(area, slow);
DrawOwnTrades(area);
}
}
private void OnProcess(ICandleMessage candle, decimal fastVal, decimal slowVal)
{
if (candle.State != CandleStates.Finished)
return;
if (!_isReady)
{
_prevFast = fastVal;
_prevSlow = slowVal;
_isReady = true;
return;
}
// Fast crosses above slow = buy
if (_prevFast <= _prevSlow && fastVal > slowVal)
{
if (Position < 0)
BuyMarket();
if (Position <= 0)
BuyMarket();
}
// Fast crosses below slow = sell
else if (_prevFast >= _prevSlow && fastVal < slowVal)
{
if (Position > 0)
SellMarket();
if (Position >= 0)
SellMarket();
}
_prevFast = fastVal;
_prevSlow = slowVal;
}
}
import clr
clr.AddReference("StockSharp.Messages")
clr.AddReference("StockSharp.Algo")
clr.AddReference("StockSharp.Algo.Indicators")
clr.AddReference("StockSharp.Algo.Strategies")
from System import TimeSpan
from StockSharp.Messages import DataType, CandleStates
from StockSharp.Algo.Indicators import SimpleMovingAverage
from StockSharp.Algo.Strategies import Strategy
class swetten_strategy(Strategy):
"""Fast/slow SMA crossover (8/34)."""
def __init__(self):
super(swetten_strategy, self).__init__()
self._fast_period = self.Param("FastPeriod", 8).SetDisplay("Fast SMA", "Fast SMA period", "Indicators")
self._slow_period = self.Param("SlowPeriod", 34).SetDisplay("Slow SMA", "Slow SMA period", "Indicators")
self._candle_type = self.Param("CandleType", DataType.TimeFrame(TimeSpan.FromMinutes(5))).SetDisplay("Candle Type", "Candle type for strategy", "General")
@property
def CandleType(self): return self._candle_type.Value
@CandleType.setter
def CandleType(self, value): self._candle_type.Value = value
def OnReseted(self):
super(swetten_strategy, self).OnReseted()
self._prev_fast = 0
self._prev_slow = 0
self._is_ready = False
def OnStarted2(self, time):
super(swetten_strategy, self).OnStarted2(time)
self._prev_fast = 0
self._prev_slow = 0
self._is_ready = False
fast = SimpleMovingAverage()
fast.Length = self._fast_period.Value
slow = SimpleMovingAverage()
slow.Length = self._slow_period.Value
sub = self.SubscribeCandles(self.CandleType)
sub.Bind(fast, slow, self.OnProcess).Start()
area = self.CreateChartArea()
if area is not None:
self.DrawCandles(area, sub)
self.DrawIndicator(area, fast)
self.DrawIndicator(area, slow)
self.DrawOwnTrades(area)
def OnProcess(self, candle, fast_val, slow_val):
if candle.State != CandleStates.Finished:
return
if not self._is_ready:
self._prev_fast = fast_val
self._prev_slow = slow_val
self._is_ready = True
return
if self._prev_fast <= self._prev_slow and fast_val > slow_val:
if self.Position < 0:
self.BuyMarket()
if self.Position <= 0:
self.BuyMarket()
elif self._prev_fast >= self._prev_slow and fast_val < slow_val:
if self.Position > 0:
self.SellMarket()
if self.Position >= 0:
self.SellMarket()
self._prev_fast = fast_val
self._prev_slow = slow_val
def CreateClone(self):
return swetten_strategy()