Pine Script Risk Management

How to Code Stop Loss and Take Profit in Pine Script

In Pine Script strategies, stop loss and take profit are managed through strategy.exit() by specifying price levels via stop and limit parameters, or point offsets via loss and profit. For dynamic risk management, stop levels are calculated using volatility indicators like ta.atr() or updated dynamically to entry price (break-even) once the market advances past a predefined profit milestone.

Build SL/TP Logic with AI Agent

Stop Loss and Take Profit approaches in Pine Script: Points vs. Price levels

When writing risk management rules in Pine Script, developers choose between two syntax models in strategy.exit(): relative offsets (loss and profit) or absolute price levels (stop and limit). Using absolute price levels is generally preferred for advanced strategies because it accommodates technical chart levels, swing highs/lows, and ATR bands directly.

MethodParameters usedInput unitsBest suited for
Price level exitstop = price, limit = priceExact currency price (e.g. $145.20)ATR stops, swing low/high defense, support/resistance exits
Point offset exitloss = ticks, profit = ticksSymbol ticks (mintick multiples)Fixed pip/tick scalping strategies
Percent exitstop = entry * (1 - pct)Calculated absolute pricePortfolio equity modeling and trend investing
Break-even exitDynamic stop = entry_priceUpdated price upon profit triggerRisk-free profit protection

Complete Pine Script v6 ATR stop loss and break-even strategy code

The following complete Pine Script v6 strategy demonstrates how to enter on a Donchian breakout, set an initial ATR stop loss, target a 2:1 profit ratio, and automatically ratchet the stop loss to break-even once price achieves 1R in profit.

Pine Script v6: Strategy with ATR stop loss and break-even triggerpinescript
//@version=6
strategy("ATR Stop Loss & Break-Even [v6]", overlay = true, initial_capital = 10000, default_qty_type = strategy.percent_of_equity, default_qty_value = 10)

// Inputs
lengthChannel = input.int(20, "Donchian Length")
atrLength = input.int(14, "ATR Length")
atrMultiplier = input.float(1.5, "ATR Stop Multiplier")
riskRewardRatio = input.float(2.0, "Risk:Reward Ratio")
enableBreakEven = input.bool(true, "Enable Break-Even Stop")

// Calculations
highestHigh = ta.highest(high, lengthChannel)[1]
lowestLow = ta.lowest(low, lengthChannel)[1]
atrVal = ta.atr(atrLength)

plot(highestHigh, "Channel High", color = color.green)
plot(lowestLow, "Channel Low", color = color.red)

// Entry trigger
longCondition = ta.crossover(close, highestHigh)

if longCondition and strategy.position_size == 0
    strategy.entry("Long", strategy.long)

// Dynamic exit calculation
if strategy.position_size > 0
    entryPrice = strategy.position_avg_price
    riskDistance = atrVal * atrMultiplier
    initialStop = entryPrice - riskDistance
    targetPrice = entryPrice + (riskDistance * riskRewardRatio)
    
    // Check if price reached 1R profit for break-even trigger
    beTriggerPrice = entryPrice + riskDistance
    isBreakEvenActive = enableBreakEven and (high >= beTriggerPrice)
    
    // Select active stop level
    activeStop = isBreakEvenActive ? math.max(initialStop, entryPrice) : initialStop
    
    strategy.exit("Exit Long", from_entry = "Long", stop = activeStop, limit = targetPrice)

Coding ATR-based dynamic stop loss

Using ta.atr() to size stops prevents getting stopped out by routine noise while maintaining tight defense when markets tighten. Key considerations when coding ATR stops include:

  • Anchor to entry bar ATR: Store the ATR value at the exact time of order fill using var or strategy.position_avg_price offsets so your stop loss does not expand retroactively as volatility increases during an open trade.
  • Symmetric risk for short positions: For short entries, add the ATR multiplier to the entry price: entryPrice + (atr * mult).
  • Account for spread and slippage: Always leave a minimum buffer beyond recent swing extremes so normal bid-ask spread does not trigger accidental stops.

How to move stop loss to break-even safely

Moving a stop loss to break-even creates a "free trade" scenario, but doing so too early cuts off profitable moves prematurely. Follow these guidelines when coding break-even logic:

  • Wait for minimum 1R extension: Moving to break-even before price has moved at least 1x your initial risk frequently results in chop exits before the trend establishes.
  • Add a tick buffer above entry: True break-even should cover execution commission and exchange fees. Set stop = entryPrice + (syminfo.mintick * 5) for longs.
  • Never move stops in reverse: Ensure your stop updating logic uses math.max() for long trades so an updated stop can only move in favor of your position, never backward.
Where Pineify fits

Pine Script AI Coding Agent

Generate robust stop loss, take profit, break-even ratchets, and multi-target exit rules in Pine Script v6 with zero syntax errors.

Also useful: Strategy Optimizer. Test different ATR stop multipliers and risk-reward ratios systematically to identify the optimal risk settings for your strategy.

Build SL/TP Logic with AI Agent

Frequently asked questions

Risk management logic limits trade losses in backtesting models but cannot eliminate execution risks such as slippage, market gaps, or broker liquidation in live markets.

Sources and verification