Pine Script: The Complete Guide for Algorithmic Traders
Pine Script is the most beginner-friendly language in trading. This guide takes you from "I've never written code" to "my live bot is running on MT5."
Why Pine Script Wins for Retail Traders
Most algorithmic-trading languages were built for institutions. MQL5 is C-like and unforgiving. Python with QuantConnect has a learning curve before you write a single buy signal. C# for NinjaTrader demands an IDE.
Pine Script started in 2014 as TradingView's tiny scripting language for custom indicators. By 2018, it had grown into a real strategy language. Today (Pine Script v5) it is the most-deployed retail trading DSL on earth — over 5 million scripts in TradingView's public library, and most of them work without modification on a backtest engine.
The reason it wins is the absence of ceremony. A complete EMA crossover strategy is eight lines of Pine Script:
//@version=5
strategy("EMA Crossover 9/21", overlay=true)
fast = ta.ema(close, 9)
slow = ta.ema(close, 21)
if ta.crossover(fast, slow)
strategy.entry("Long", strategy.long)
if ta.crossunder(fast, slow)
strategy.close("Long")That's a complete, deployable trading bot. You can run that on PineForge right now and see it execute on real gold or BTC charts. No imports, no configuration, no boilerplate.
The cost of this simplicity? Pine Script is *not* general-purpose. You can't make HTTP calls. You can't read files. You can't build a UI outside of charts. For 95% of retail trading needs, that's the right trade.
Pine Script Anatomy: The Five Building Blocks
Every Pine Script strategy reduces to five concepts. Master these and you can read any strategy on the platform.
1. The version pragma and declaration
//@version=5
strategy("My Strategy", overlay=true, initial_capital=10000, commission_type=strategy.commission.percent, commission_value=0.05)The first line declares the Pine Script version. The second declares whether this is an *indicator* (visualisation only — indicator(...)) or a *strategy* (can place orders — strategy(...)). PineForge accepts strategy scripts only.
2. Input parameters
fast_len = input.int(9, "Fast EMA Length")
slow_len = input.int(21, "Slow EMA Length")
risk_pct = input.float(1.0, "Risk per trade (%)", minval=0.1, maxval=5.0)Inputs are how you parameterise a strategy. They show up as adjustable fields in PineForge's bot configuration. Always use input.* for any number you might want to tune later — magic numbers are a debugging nightmare.
3. Series and indicator functions
Pine Script's core abstraction is the time series — a value that changes per bar. close, high, low, open, volume are all series. Every indicator returns a series.
ema = ta.ema(close, 21) // EMA of close price
rsi = ta.rsi(close, 14) // RSI
[macd, signal, hist] = ta.macd(close, 12, 26, 9) // MACD with three outputs
atr = ta.atr(14) // Average True RangeThe ta namespace contains over 100 built-in functions. See the glossary on EMA, RSI, and ATR for what they actually compute.
4. Conditions and crossovers
long_signal = ta.crossover(fast, slow) and rsi < 70ta.crossover(a, b) returns true *only on the bar where a moves above b* — not while a > b continues to hold. This is the difference between an entry signal (one-shot) and a state (continuous). Most beginner mistakes confuse the two. See the crossover glossary entry.
5. Order execution
if long_signal
strategy.entry("Long", strategy.long)
strategy.exit("TP/SL", from_entry="Long",
stop=strategy.position_avg_price - atr * 2,
limit=strategy.position_avg_price + atr * 4)strategy.entry() opens a position. strategy.exit() sets stop-loss and take-profit (with bracket orders). strategy.close() closes immediately. The bot in production maps these calls 1:1 to real broker orders.
That's it. Five concepts. Anyone who tells you Pine Script is hard hasn't spent 30 minutes with the docs.
Your First Strategy in 10 Minutes
Let's build something tradeable. Goal: an EMA crossover with an RSI filter and ATR-based stops, deployable on XAUUSD.
//@version=5
strategy("Gold EMA + RSI Filter", overlay=true,
initial_capital=10000,
commission_type=strategy.commission.percent,
commission_value=0.04,
default_qty_type=strategy.percent_of_equity,
default_qty_value=10)
// Inputs
fast_len = input.int(9, "Fast EMA")
slow_len = input.int(21, "Slow EMA")
rsi_len = input.int(14, "RSI Length")
rsi_max = input.int(70, "RSI Filter (block longs above)")
atr_len = input.int(14, "ATR Length")
atr_mult = input.float(2.5, "ATR Stop Multiple", minval=1.0, maxval=5.0)
// Indicators
fast = ta.ema(close, fast_len)
slow = ta.ema(close, slow_len)
rsi = ta.rsi(close, rsi_len)
atr = ta.atr(atr_len)
// Entry
long_cond = ta.crossover(fast, slow) and rsi < rsi_max
if long_cond
strategy.entry("Long", strategy.long)
// Exit — ATR-based stop, EMA crossback
if strategy.position_size > 0
stop = strategy.position_avg_price - atr * atr_mult
strategy.exit("ATR Stop", from_entry="Long", stop=stop)
if ta.crossunder(fast, slow)
strategy.close("Long")Drop this into PineForge → Strategies → New → paste → Save. Run a backtest on XAUUSD H1 over the last 12 months. You should see something like:
| Metric | Result |
|---|---|
| Net return | +43% |
| Win rate | 47% |
| Profit factor | 1.62 |
| Max drawdown | -8.2% |
| Sharpe | 1.34 |
These numbers won't match exactly because data and broker spreads vary, but the order of magnitude should be similar. If you get profit factor 0.8 — great, the strategy doesn't work on your data. If you get profit factor 4.5 — the backtest is overfit, see the overfitting glossary.
Indicators That Matter (and the Math Behind Them)
You'll find 100+ functions in Pine Script's ta namespace. Most of them are useless for retail strategies. The ten below cover ~95% of what works.
Trend
- EMA / SMA — moving averages. EMA reacts faster, SMA is smoother. See EMA, SMA.
- MACD — difference between two EMAs. Crossovers signal momentum shifts. See MACD.
- ADX — strength of trend (not direction). > 25 = trending, < 20 = ranging.
Mean reversion
- RSI — oscillates 0-100. > 70 overbought, < 30 oversold. See RSI.
- Stochastic — like RSI but more sensitive. Good for short-term mean reversion.
- Bollinger Bands — volatility-adaptive channels. See Bollinger Bands.
Volatility & risk
- ATR — Average True Range. The single best input for stop sizing. See ATR.
- Standard deviation — used internally by Bollinger Bands but useful directly.
Volume & flow
- Volume profile — distribution of volume by price. Powerful but data-intensive.
- VWAP — volume-weighted average price. Institutions watch this; you should too on intraday.
If you understand these ten and how to combine them, you can build any strategy in this library.
Backtesting Properly: What the Tester Hides
Pine Script's backtest engine is excellent — but it lies to you in three specific ways.
It assumes perfect fills. Your stop at $1,950 fills at $1,950. In live markets, slippage might fill you at $1,948.50. PineForge's backtest engine models this; TradingView's basic tester does not.
It uses bar-close logic. A signal that fires *during* a 1H bar doesn't execute until the bar closes. In live trading, the same signal could fire at any second. This causes backtest-vs-live divergence on lower timeframes.
It doesn't include funding/swap. A strategy that holds positions overnight pays swap fees. On EUR/USD long, that's ~3% annualised. A strategy that looks like profit factor 1.4 in backtest can be 1.1 after swaps.
The fix: read why backtest before you trade for the full discipline, including walk-forward analysis and out-of-sample testing.
From Pine Script to Live Trading on MT5
Pine Script on TradingView only paper-trades or sends webhooks. To trade live, you need a runtime that:
- Parses your Pine Script,
- Connects to a broker,
- Translates
strategy.entry()calls into real orders, - Manages position sizing, risk, and reconnection.
PineForge does this. You write Pine Script in our editor (or paste from TradingView), connect your Exness MT5 account, click "Deploy", and the strategy runs 24/5 on real candles.
What's running under the hood:
- Pine parser converts your script to an AST.
- A bar-by-bar interpreter walks the AST against live OHLC data.
strategy.entry()calls hit MT5 via MetaAPI (broker-grade execution).- Risk and position sizing are applied per the bot configuration.
A 200-line Pine Script strategy in TradingView and the live PineForge bot produce identical signals. We've validated this on over 28 strategies.
Common Mistakes That Sink Strategies
After deploying hundreds of bots, these are the patterns that ruin promising strategies in live trading.
1. Repainting
A strategy that "looks" profitable but uses future bars secretly. Common offenders: request.security() without proper barmerge.lookahead_off, indicators that recalculate when the bar repaints. Fix: only use confirmed bars (barstate.isconfirmed) for entries.
2. Survivorship bias on a single asset
Strategy works great on XAUUSD. You deploy it on EURUSD. It loses 20% in a week. Different asset, different volatility regime. Fix: backtest across at least 5 uncorrelated symbols. If it works on only one, it's curve-fit.
3. Not modelling spread
Your TradingView backtest assumes zero spread. Your real broker charges 0.3 pips on EUR/USD. Over 1000 trades that's a -300 pip drag — kills most edges. Fix: PineForge's backtest engine models real broker spreads; verify there.
4. Static stops in volatile markets
A 30-pip stop that works in calm London session blows out in news. Fix: ATR-based stops adapt automatically — see ATR Trend Follow.
5. No regime filter
A trend strategy fired in a range chops you to death. A mean-reversion strategy fired in a trend rides you to a margin call. Fix: gate entries with ADX > 25 (trend regime) or ADX < 20 (range regime).
What's Next: Multi-Timeframe, Libraries, and Optimisation
Once you've shipped your first profitable bot, the next levels:
Multi-timeframe strategies — confirm a 1H entry only when the 4H trend agrees. Use request.security() carefully (the repainting trap above).
Pine Script libraries — reusable code modules. Once you've written the same risk-management block three times, library it.
Strategy optimisation — use walk-forward analysis to find parameters that generalise. Avoid the overfitting trap of "just optimise everything."
Portfolio of bots — run multiple uncorrelated strategies on multiple symbols. Diversification reduces drawdown more than any single optimisation.
This is a 32-minute introduction. There are years of depth beyond it. But you can start trading bots tomorrow with what's in this guide.
Sign up for PineForge, pick any strategy, and run it. Your first backtest takes 30 seconds. Your first live deployment takes another two minutes. Stop reading and start shipping.
Stop reading. Start trading.
Pick a strategy, backtest in 30 seconds, deploy in 2 minutes.
