Edgoro
Indicator · Markers, drawings and colors

Pine Script bgcolor, fill and barcolor examples (v6)

Color a TradingView chart from Pine Script v6: a fill between two averages, a background shaded by RSI with color.from_gradient(), candles colored by volume.

Short answer

bgcolor(color) shades the background of each bar, fill(plot1, plot2, color) shades the area between two plots (or two hlines), and barcolor(color) recolors the candles. All three take a color that can change on every bar, with na for no color, so the condition goes into the color: bgcolor(cond ? color.new(color.green, 85) : na).

The script

An EMA cloud that changes color with the trend, a background that darkens as RSI goes further past 70 or under 30, and candles highlighted on high volume. Paste it into a new indicator in the Pine Editor, then save and add it to the chart.

Pine Script v6
//@version=6
indicator("Background, fill and bar colors", overlay = true)

fastLen = input.int(20, "Fast EMA", minval = 1)
slowLen = input.int(50, "Slow EMA", minval = 2)
rsiLen  = input.int(14, "RSI length", minval = 2)
volMult = input.float(1.5, "High volume (x 20-bar average)", minval = 1, step = 0.1)

fast   = ta.ema(close, fastLen)
slow   = ta.ema(close, slowLen)
rsi    = ta.rsi(close, rsiLen)
volAvg = ta.sma(volume, 20)

bool bull = fast > slow

// fill() works on plot IDs: keep what plot() returns
pFast = plot(fast, "Fast EMA", bull ? color.teal : color.red)
pSlow = plot(slow, "Slow EMA", color.gray)
fill(pFast, pSlow, bull ? color.new(color.teal, 80) : color.new(color.red, 80), "Trend cloud")

// Background: transparent at 70, stronger as RSI rises to 90 (and the mirror below 30)
color hotColor  = color.from_gradient(rsi, 70, 90, color.new(color.red, 100), color.new(color.red, 70))
color coldColor = color.from_gradient(rsi, 10, 30, color.new(color.green, 70), color.new(color.green, 100))
bgcolor(rsi > 70 ? hotColor : rsi < 30 ? coldColor : na, title = "RSI extremes")

// Candles: strong up or down bars on high volume, on the right side of the slow EMA
bool bigVolume  = volume > volMult * volAvg
bool strongUp   = bigVolume and close > open and close > slow
bool strongDown = bigVolume and close < open and close < slow
barcolor(strongUp ? color.lime : strongDown ? color.fuchsia : na, title = "High-volume bars")

How it works

  • pFast = plot(...). plot() returns an ID, and fill() takes two of them. It can't take the values themselves, and it can't mix a plot ID with an hline ID.
  • Colors that change per bar. plot(), fill(), bgcolor() and barcolor() all accept a series color, so one call covers both trend states. color.new(color.teal, 80) sets the transparency: 0 is opaque, 100 invisible; 80–95 keeps candles readable.
  • color.from_gradient(value, bottom, top, bottomColor, topColor) blends between two colors as value moves from bottom to top, and clamps outside that range. Here the background goes from invisible at RSI 70 to 70% transparent red at 90.
  • na means no color. The ternaries return na on ordinary bars, so the background and candles keep their normal look there.
  • title names each element in the Style tab, where the user can hide or recolor it.

Pitfalls

  • Calling them in an if block. if bull followed by bgcolor(...) gives Cannot use bgcolor in local scope. Put the condition in the color instead: bgcolor(bull ? color.new(color.teal, 90) : na).
  • The old transp argument. bgcolor(color.red, transp = 80) is v4 code: v6 removed transp (the transp argument page). Use color.new(color.red, 80).
  • A moving level with hline(). hline() draws a fixed level, so hline(ta.sma(close, 50)) fails with series float vs input float. Plot the moving value, and fill between plots.
  • Filling plot values instead of IDs. fill(fast, slow, ...) passes two series of prices, which fill() doesn't accept. Pass what plot() returned.
  • A fill with hidden lines. To show only the cloud, keep the plots but give them a fully transparent color (color.new(color.gray, 100)): the fill still needs the two plots to exist.

Variations

Zones in an oscillator pane. fill() between two hline() levels shades a fixed zone, and a fill between the RSI plot and an invisible midline shows which side of 50 it is on.

//@version=6
indicator("RSI with filled zones", overlay = false)
rsi = ta.rsi(close, 14)
h70 = hline(70, "Overbought", color.gray)
h30 = hline(30, "Oversold", color.gray)
fill(h70, h30, color.new(color.blue, 92), "Neutral zone")
pRsi = plot(rsi, "RSI", color.purple)
pMid = plot(50, "Midline", color.new(color.gray, 100))
fill(pRsi, pMid, rsi > 50 ? color.new(color.teal, 80) : color.new(color.red, 80), "Above or below 50")

Background during a session. bgcolor(not na(time(timeframe.period, "0930-1600", "America/New_York")) ? color.new(color.blue, 92) : na) shades the New York cash session; the session filter guide covers time zones and overnight sessions.

Questions

How do I fill between two lines in Pine Script?

Keep the IDs returned by plot(), for example p1 = plot(fast) and p2 = plot(slow), then call fill(p1, p2, color.new(color.teal, 80)). The color can change per bar. For two fixed levels, use the IDs returned by hline().

How do I color candles in Pine Script?

Call barcolor() at the top level with a color expression, for example barcolor(close > open and volume > ta.sma(volume, 20) ? color.lime : na). Bars where the expression is na keep their normal color.

Why does my background color hide the candles?

The color is too opaque. In color.new(color, transparency), 0 is opaque and 100 invisible: backgrounds usually read well between 80 and 95.

Every script on this page was checked with Edgoro Pine Check (Pine Script v6 rules). Pine Check is a static checker, not TradingView's compiler: TradingView compiles the script when you save it in the Pine Editor. The scripts are examples to learn from, not trading systems. Trading involves substantial risk of loss and is not suitable for every investor. Edgoro is a software tool, not a broker or financial adviser: nothing it produces is investment advice, and past or backtested performance does not guarantee future results.

Need a different version of this script?

Describe the change in plain English and Edgoro writes the Pine Script v6 for you, checked with Pine Check. For example:

“Fill the area between the 20 and 50 EMA in green or red by trend, shade the background when RSI is above 70 or below 30, and color high-volume candles.”