In TradingView we can colour the chart’s full background (from top to bottom) and colour a background section. But how do several background areas laid on top of each other work?

In this article:

Repeatedly colouring a background area in TradingView Pine

We can use basic TradingView colours and hexadecimal colour values with TradingView functions like fill(). That function colours the chart’s background that’s between two plots or two horizontal lines (Pine Script Language Tutorial, n.d.).

To know between which plots or horizontal lines the background should be filled, fill() either requires two plot objects (which are returned by the plot() function) or two horizontal line objects that the the hline() function returns (TradingView, n.d.). These objects represent an instance of a plot or horizontal line, just like a string variable represent a certain text and a numerical variable a value. For more on fill() and its different arguments, see colouring part of the chart’s background in TradingView.

The fill() function can colour the background of support and resistance areas and shade the background between a plot and line. We can even use it to colour the background between invisible plots. Another application of fill() is overlaying coloured background areas on top of each other, which we achieve by using this function several times in the same script. To see how, let’s look at an example indicator.

Combining coloured TradingView background areas

In the example script below we colour two background areas with fill(). The first is between the highest high and lowest low of a 30-bar period. Inside that background section we colour the area between the highest high and lowest low of 10 recent price bars. This way our coloured backgrounds provide a rough trend indication: a beginning trend has bars moving outside the 10-bar highs and lows while strong trends have prices move beyond the 30-bar extremes.

After discussing the code, we’ll look at charts showing the indicator and how the fill() function order affects the indicator. But first the code:

study(title="Colouring background areas repeatedly", overlay=true)

// Inputs
shortLookback = input(title="Short lookback", type=integer, 
     defval=10, minval=3)
longLookback  = input(title="Long lookback", type=integer, 
     defval=30, minval=10)
smoothLength  = input(title="Double-smooth length", type=integer, 
     defval=7, minval=1)
plotOffset    = input(title="Plot offset", type=integer, 
     defval=1, minval=0)

// Compute values
highestValue   = highest(high, shortLookback)
highestSmooth1 = sma(highestValue, smoothLength)
highestSmooth2 = sma(highestSmooth1, smoothLength)

highestHi = highestSmooth2
lowestLo  = sma(sma(lowest(low, shortLookback), smoothLength), smoothLength)

// Plot values
highPlot = plot(series=highestHi, color=orange, linewidth=2)
lowPlot  = plot(series=lowestLo, color=orange, linewidth=2)

highestPlot = plot(series=highest(high, longLookback)[plotOffset], 
     color=#1E90FF)
lowestPlot  = plot(series=lowest(low, longLookback)[plotOffset], 
     color=#1E90FF)

// Fill background areas
fill(plot1=highestPlot, plot2=lowestPlot, color=#1E90FF, transp=80)

fill(plot1=highPlot, plot2=lowPlot, color=#FFD700, transp=80)

We start with the study() function to set the indicator’s properties. With this function’s overlay argument set to true the script displays on the main data series and not in a separate chart pane (TradingView, n.d.).

Then we add several input options to the script:

shortLookback = input(title="Short lookback", type=integer, 
     defval=10, minval=3)
longLookback  = input(title="Long lookback", type=integer, 
     defval=30, minval=10)
smoothLength  = input(title="Double-smooth length", type=integer, 
     defval=7, minval=1)
plotOffset    = input(title="Plot offset", type=integer, 
     defval=1, minval=0)

These inputs are integer inputs, meaning they create a numerical option in the script’s settings that accepts whole numbers only (Pine Script Language Tutorial, n.d.). For this we set the type argument of the input() function to integer (TradingView, n.d.). Besides creating the input itself, input() also returns the setting’s current value. We store those values in variables here with the assignment operator (=). That way we can refer to the input’s current value later on in the script by using the variable.

The first input has its title argument set to “Short lookback”, and this text is what’s placed before the input option in the script’s settings window (Pine Script Language Tutorial, n.d.). Its default value (defval) is set to 10 and the minval argument, which sets the input’s minimum allowed value (TradingView, n.d.), is set to 3 here. The current value of this input is stored in the shortLookback variable, and we’ll use that variable for setting the shortest period that we compute the highest high and lowest low values on.

The next input is named “Long lookback” with a standard value of 30 and a minimum value of 10. This input will set the longest period for determining the highest high and lowest low, and to reference its value later on we store its value in the longLookback variable.

The smoothLength variable holds the value of the third input that’s named “Double-smooth length”. It has a default value of 7 with a minimum of 1, and we use it to perform the smoothing of the highest high and lowest low from the shortest lookback period.

The last input is titled “Plot offset” and has a default of 0. With its minval argument set to 0 we ensure that the plotOffset input variable always has a positive value. We use that variable when plotting the highest high and lowest low of the longest lookback period. By offsetting those plotted lines we can see price breakouts, which wouldn’t be possible if the highest high and lowest low also include the current bar.

After making the inputs the highest high and lowest low from the shortest period are averaged:

highestValue   = highest(high, shortLookback)
highestSmooth1 = sma(highestValue, smoothLength)
highestSmooth2 = sma(highestSmooth1, smoothLength)

highestHi = highestSmooth2
lowestLo  = sma(sma(lowest(low, shortLookback), smoothLength), smoothLength)

We smooth the highest high and lowest low with two approaches here: one uses interim variables to make the intermediate steps clear while the other uses a single statement.

To average the highest high we first retrieve that value with highest(). That function accepts two arguments: a series of values and an integer to set the number of bars to get the highest value of (TradingView, n.d.). We set that first argument to the bar’s high (high) while the length is specified with the shortLookback input variable. When this “Short lookback” input is set to its default value, the highest() function returns the 10-bar high (including the current bar). We store that returned value in the highestValue variable.

That variable is then averaged for the first time with sma(). This function computes a Simple Moving Average (SMA) and needs two arguments: a series of values alongside an integer that sets the SMA length (TradingView, n.d.). With these arguments set to highestValue and smoothLength we get the 7-bar average of the 10-bar high. That value is subsequently assigned to the highestSmooth1 variable.

To perform the double-smoothing, we average that value again with the sma() function. This time we use the highestSmooth1 and smoothLength variables inside that function’s parentheses. With this the sma() function calculates the 7-bar average of the already-averaged 10-bar high, and we store that value in the highestSmooth2 variable. For consistent naming, we put that variable’s value in the highestHi variable for use later on.

However, these different steps can be reduced into a single line of code. We do that when setting the value of the lowestLo variable to a single line of code with the lowest() and sma() functions in it. When functions are placed inside parentheses of other functions, TradingView Pine evaluates the innermost function first and then works from the inside out. This means that lowest(low, shortLookback) is evaluated first to get the 10-bar lowest low (including the current bar).

That value is then used with the next function; the inner sma() function that smooths the 10-bar low with the smoothLength number of bars. In the next step, this 7-bar average value of the lowest low is averaged again by the outer sma() function. This second sma() function also calculates on the smoothLength number of bars, and the value it returns is subsequently assigned to the lowestLo variable.

Next up is plotting some values:

highPlot = plot(series=highestHi, color=orange, linewidth=2)
lowPlot  = plot(series=lowestLo, color=orange, linewidth=2)

highestPlot = plot(series=highest(high, longLookback)[plotOffset], 
     color=#1E90FF)
lowestPlot  = plot(series=lowest(low, longLookback)[plotOffset], 
     color=#1E90FF)

We plot values on the chart with the plot() function, which displays the data that’s set by its series argument (TradingView, n.d.). That data is then plotted as a continuous line by default. The plot() function also returns a plot’s object (TradingView, n.d.), and here we store those objects in variables with the assignment operator (=). That way we can refer to them afterward when colouring the background sections.

The first plot() function call has its series argument set to the highestHi variable to plot the double-smoothed highest high. We set this line’s colour to the orange standard TradingView colour and its linewidth argument is set to 2. That argument specifies the plot’s size with a value ranging from 1 (default) to 4 for the thickest plot (TradingView, n.d.). We store the plot object that’s returned by plot() here in the highPlot variable.

The second plot() function call is similar to the first and displays the lowestLo variable on the chart. These double-smooted lowest low values display as an orange line, and we assign the plot’s object to the lowestLo variable.

With the next two statements we plot the 30-bar highest high and lowest low on the chart (assuming the “Long lookback” input is still set to its standard value of 30). The first of these plot() function calls has its series argument set to the highest() function, which calculates on the bar’s high prices (price) with a length that’s set with the longLookback number of bars. This returns the highest high including the current bar. That latter is troubling because, if we plot a highest high line that include the current bar’s value, then a price bar can never break outside that range.

We fix that by placing the history referencing operator ([]) just behind the highest() function and pass in the plotOffset input variable in its square brackets. That operator, when placed behind a value, returns that value’s previous bar value (Pine Script Language Tutorial, n.d.). So when we use the operator in this way, we plot the highest high value for a plotOffset number of bars back. For instance, when that input variable is set to 1, we plot the highest high value of the previous bar on the current bar. And that way the current bar’s high can still ‘break out’ the highest high.

The benefit of using the plotOffset input variable is that we can manually specify in the script’s settings how many bars the plot should be shifted to previous bars. The colour of this highest high line is set to #1E90FF, the hexadecimal colour value of dodger blue. We store the plot object returned by plot() in the highestPlot variable.

The lowest low of the longer lookback period is plotted in a similar way. Now we set the series argument to the lowest() function based on the bar’s low (low) and the longLookback input variable. To ensure that prices can drop below this dodger-blue line, we again shift the plotted values with the history referencing operator and the plotOffset variable. We store this plot’s object in the lowestPlot variable.

We then fill the background between the plots:

fill(plot1=highestPlot, plot2=lowestPlot, color=#1E90FF, transp=80)

fill(plot1=highPlot, plot2=lowPlot, color=#FFD700, transp=80)

The fill() function colours a background section and its plot1 and plot2 arguments specify between which plot objects that background area should be coloured (TradingView, n.d.). In the first fill() statement we set those arguments to the 30-bar highest high (highestPlot) and lowest low (lowestPlot) lines. The function’s color argument is set to #1E90FF while its transparency is four-fifths (transp=80).

We end the example with a second fill() statement that colours the background between the double-smoothed 10-bar highest high (highPlot) and lowest low (lowPlot). This background section is coloured with #FFD700, the hexadecimal colour value of gold, and its transparency is set to 80% (transp=80).

Overlaying coloured background sections in TradingView

When we add the above example to a S&P 500 Index CFD chart, it looks like:

Combining coloured backgrounds in TradingView

And applied to a GBP/USD chart, the example displays as:

Programmatically applying coloured backgrounds in TradingView

The script’s input options are the following:

Example of the TradingView script's input options

Now let’s change those settings to a ‘Plot Offset’ of 3, a ‘Double-smooth Length’ value of 10, and a ‘Short Lookback’ period of 25. The previous GBP/USD chart now changes to:

Coloured TradingView backgrounds on top of each other

Colouring backgrounds differently: the effect of statement order

When fill() is used repeatedly in a script, the order in which we place those fill() statements matters. That’s because the first fill() function call creates the undermost coloured background area, and any subsequent fill() function call creates a filled background area that’s placed on top of the previous. And so the last fill() function call creates the uppermost coloured background. This visual effect is more or less pronounced depending on the background’s transparency.

To see how this effect plays out, let’s consider the above programming example. In it, we first coloured the background between the 30-bar highest high and lowest low blue. Then we filled the background area between the 10-bar highest high and lowest low yellow:

fill(plot1=highestPlot, plot2=lowestPlot, 
     color=#1E90FF, transp=80) // blue background

fill(plot1=highPlot, plot2=lowPlot, 
     color=#FFD700, transp=80) // yellow background

This looks like:

Colouring several parts of the TradingView chart

Now let’s change the order of the fill() statements so that the yellow background is made first. For that, we change their order to the following:

fill(plot1=highPlot, plot2=lowPlot, 
     color=#FFD700, transp=80) // yellow background

fill(plot1=highestPlot, plot2=lowestPlot, 
     color=#1E90FF, transp=80) // blue background

Saving the script now changes the chart to:

Placing one coloured TradingView background behind another

The yellow background area is less visible now that it’s placed behind the blue one. But we can still see the yellow background clearly due to the high transparency of both backgrounds, which causes the yellow background to ‘shine through’ the blue one. This changes, however, when we lower the transparency to 40%:

fill(plot1=highPlot, plot2=lowPlot, 
     color=#FFD700, transp=40) // yellow background

fill(plot1=highestPlot, plot2=lowestPlot, 
     color=#1E90FF, transp=40) // blue background

This gives the following effect:

Creating solid coloured TradingView backgrounds

Now the yellow background is barely visible (and will be hidden completely if the transparency is even lower). If we swap both fill() statements again, the blue background area is again made first and the yellow one placed on top of it:

fill(plot1=highestPlot, plot2=lowestPlot, 
     color=#1E90FF, transp=40) // blue background

fill(plot1=highPlot, plot2=lowPlot, 
     color=#FFD700, transp=40) // yellow background

While both fill() statements are now in the same order as they were in the programming example discussed above, we can now clearly see how the backgrounds are overlaid on each other due to the lower transparency:

Combining coloured backgrounds in TradingView

Other things we can do with the fill() function are highlighting support and resistance areas and colouring the background of histograms and columns. The basics of fill() and its arguments are discussed in colouring part of the chart’s background in TradingView. The different colours that this function can use include the basic TradingView colours and the hexadecimal colour values.

Summary

The fill() function colours a section of the chart’s background. It fills the area that’s between two plot objects (that the plot() function returns) or between two horizontal line objects which the hline() function returns. By repeatedly using the fill() function in the same script, several background areas are coloured and placed on top of the other. The order in which we call the fill() function then matters: the first fill() function creates the undermost coloured background area. Any fill() function call after that creates a coloured background area that’s placed on top of the previous, with the last fill() statement creating the topmost coloured background section.


References

Pine Script Language Tutorial (n.d.). Retrieved on October 23, 2015, from https://docs.google.com/document/d/1sCfC873xJEMV7MGzt1L70JTStTE9kcG2q-LDuWWkBeY/

TradingView (n.d.). Script Language Reference Manual. Retrieved on December 31, 2015, from https://www.tradingview.com/study-script-reference/