Library · Pine Script v5 · Library

lower_tf

by ivansoft· code credited to PineCoders

A Pine Script v5 library for working with intrabar data from a lower timeframe.

View on GitHub

GitHub stars1on the repository
Pine versionv5runs as is
Lines of code246
Settings7inputs
LicenceNone statedfile: MPL-2.0
Last update1 year ago1 Mar 2025

Add It to Your TradingView Chart

  1. 1Copy the scriptPress Copy script above, or the copy button on the code below.
  2. 2Open the Pine EditorOpen a TradingView chart and choose Pine Editor at the bottom of the screen.
  3. 3Paste over the templateCreate a new library, select all of the template text and paste. Press Save and give it a name.
  4. 4Publish or import itA library draws nothing. Publish it from the editor, then import its functions in your own scripts.

Source Code

246 lines of Pine Script v5 from edu_lib/lower_tf.pine, published under MPL-2.0 (file header). Keep the author's credit and licence lines when you reuse it.

lower_tf.pine
// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/
// © PineCoders

//@version=5
library("lower_tf")

// LTF Library
// v4, 2023.03.25

// This code was written using the recommendations from the Pine Script™ User Manual's Style Guide:
//   https://www.tradingview.com/pine-script-docs/en/v5/writing/Style_guide.html



import PineCoders/Time/4 as PCtime



//#region ———————————————————— Constants and Inputs 


// ————— Constants
color WHITE   = color.white
color GRAY    = color.gray

string LTF1   = "Covering most chart bars (least precise)"
string LTF2   = "Covering some chart bars (less precise)"
string LTF3   = "Covering less chart bars (more precise)"
string LTF4   = "Covering few chart bars (very precise)"
string LTF5   = "Covering the least chart bars (most precise)"
string LTF6   = "~12 intrabars per chart bar"
string LTF7   = "~24 intrabars per chart bar"
string LTF8   = "~50 intrabars per chart bar"
string LTF9   = "~100 intrabars per chart bar"
string LTF10  = "~250 intrabars per chart bar"
string TT_LTF = "Your selection here controls how many intrabars will be analyzed for each chart bar. 
  The more intrabars you analyze, the more precise the calculations will be,
  but the less chart bars will be covered by the indicator's calculations because a maximum of 100K intrabars can be analyzed.\n\n
  The first five choices determine the lower timeframe used for intrabars using how much chart coverage you want.
  The last five choices allow you to select approximately how many intrabars you want analyzed per chart bar."
string TAB_TXT = "Uses intrabars at {0}\nAvg intrabars per chart bar: {1,number,#.#}\nChart bars covered: {2} of {3} ({4,number,#.##}%)"
string ERR_TXT = "No intrabar information exists at the '{0}' timeframe."

// ————— Inputs
string  ltfModeInput            = input.string(LTF3,     "Intrabar precision",         options = [LTF1, LTF2, LTF3, LTF4, LTF5, LTF6, LTF7, LTF8, LTF9, LTF10], tooltip = TT_LTF)
bool    showInfoBoxInput        = input.bool(true,       "Show information box ")
string  infoBoxSizeInput        = input.string("normal", "Size ",                      inline = "01", options = ["tiny", "small", "normal", "large", "huge", "auto"])
string  infoBoxYPosInput        = input.string("bottom", "↕",                          inline = "01", options = ["top", "middle", "bottom"])
string  infoBoxXPosInput        = input.string("left",   "↔",                          inline = "01", options = ["left", "center", "right"])
color   infoBoxColorInput       = input.color(GRAY,      "",                           inline = "01")
color   infoBoxTxtColorInput    = input.color(WHITE,     "T",                          inline = "01")
//#endregion



//#region ———————————————————— Functions 


// @function            Filters small timeframes by returning the original value if it is greater than or equal to 5 seconds, or 1 second otherwise.
// @param tfInSeconds   (simple int) A timeframe in seconds.
// @returns             (int) The filtered timeframe in seconds.
filterSmallTfs(simple int tfInSeconds) =>
    int result = tfInSeconds < 5 ? 1 : tfInSeconds


// @function            Selects a LTF from the chart's TF, depending on the `userSelection` input string.
// @param userSelection (simple string) User-selected input string which must be one of the `choicex` arguments.
// @param choice1       (simple string) Input selection corresponding to "Covering most chart bars (least precise)".
// @param choice2       (simple string) Input selection corresponding to "Covering some chart bars (less precise)".
// @param choice3       (simple string) Input selection corresponding to "Covering less chart bars (more precise)".
// @param choice4       (simple string) Input selection corresponding to "Covering few chart bars (very precise)".
// @param choice5       (simple string) Input selection corresponding to "Covering the least chart bars (most precise)".
// @param choice6       (simple string) Input selection corresponding to "~12 intrabars per chart bar".
// @param choice7       (simple string) Input selection corresponding to "~24 intrabars per chart bar".
// @param choice8       (simple string) Input selection corresponding to "~50 intrabars per chart bar".
// @param choice9       (simple string) Input selection corresponding to "~100 intrabars per chart bar".
// @param choice10      (simple string) Input selection corresponding to "~250 intrabars per chart bar".
// @returns             (simple string) A timeframe string to be used with `request.security_lower_tf()`.
export ltf( simple string userSelection,
     simple string choice1, 
     simple string choice2, 
     simple string choice3, 
     simple string choice4, 
     simple string choice5, 
     simple string choice6,
     simple string choice7,
     simple string choice8,
     simple string choice9,
     simple string choice10) =>
  
    // Qty of minutes in each reference TF.
    int  ONE_MIN    = 1
    int  ONE_SEC    = ONE_MIN  / 60
    int  ONE_HOUR   = ONE_MIN  * 60
    int  ONE_DAY    = ONE_HOUR * 24
    int  ONE_WEEK   = ONE_DAY  * 7

    float chartTfInMinutes = timeframe.in_seconds() / 60.
    bool  marketIs24Hours  = syminfo.type == "crypto" or syminfo.type == "forex"
    float marketIs24HoursFactor = marketIs24Hours ? 0.25 : 1.0

    // Determine user selection.
    bool leastPrecise = false
    bool lessPrecise  = false
    bool morePrecise  = false
    bool veryPrecise  = false
    bool mostPrecise  = false
    bool intrabars12  = false
    bool intrabars24  = false
    bool intrabars50  = false
    bool intrabars100 = false
    bool intrabars250 = false
    switch userSelection
        choice1  => leastPrecise := true
        choice2  => lessPrecise  := true
        choice3  => morePrecise  := true
        choice4  => veryPrecise  := true
        choice5  => mostPrecise  := true
        choice6  => intrabars12  := true
        choice7  => intrabars24  := true
        choice8  => intrabars50  := true
        choice9  => intrabars100 := true
        choice10 => intrabars250 := true
    
    // Find the LTF corresponding to user's selection.
    string result =
      switch
        leastPrecise => PCtime.secondsToTfString(timeframe.in_seconds() / 4)
        veryPrecise  =>             
            switch
                chartTfInMinutes <= ONE_HOUR      => "5S"
                chartTfInMinutes <= ONE_HOUR * 2  => "15S"
                chartTfInMinutes <= ONE_HOUR * 4  => "30S"
                chartTfInMinutes <= ONE_HOUR * 12 => marketIs24Hours ? "1"  : "30S"
                chartTfInMinutes <= ONE_DAY       => marketIs24Hours ? "2"  : "1"
                chartTfInMinutes <= ONE_WEEK      => marketIs24Hours ? "15" : "5"
                =>                                   marketIs24Hours ? "60" : "30"
        mostPrecise  =>             
            switch
                chartTfInMinutes <= ONE_HOUR      => "1S"
                chartTfInMinutes <= ONE_HOUR * 2  => "5S"
                chartTfInMinutes <= ONE_HOUR * 4  => "15S"
                chartTfInMinutes <= ONE_HOUR * 12 => marketIs24Hours ? "30S" : "15S"
                chartTfInMinutes <= ONE_DAY       => marketIs24Hours ? "1"   : "30S"
                chartTfInMinutes <= ONE_WEEK      => marketIs24Hours ? "10"  : "3"
                =>                                   marketIs24Hours ? "30"  : "15"
        lessPrecise  =>
            switch
                chartTfInMinutes <= ONE_MIN       => "5S"
                chartTfInMinutes <= ONE_MIN * 2   => "10S"
                chartTfInMinutes <= ONE_MIN * 3   => "15S"
                chartTfInMinutes <= ONE_MIN * 5   => "30S"
                chartTfInMinutes <= ONE_MIN * 15  => "1"
                chartTfInMinutes <= ONE_HOUR      => "3"
                chartTfInMinutes <  ONE_HOUR * 2  => "5"
                chartTfInMinutes <  ONE_HOUR * 4  => "15"
                chartTfInMinutes <  ONE_HOUR * 6  => "30"
                chartTfInMinutes <  ONE_HOUR * 12 => marketIs24Hours ? "60"  : "30"
                chartTfInMinutes <  ONE_DAY       => marketIs24Hours ? "120" : "30"
                chartTfInMinutes <  ONE_WEEK      => marketIs24Hours ? "720" : "120"
                => "D"
        morePrecise =>
            switch
                chartTfInMinutes <= ONE_MIN       => "1S"
                chartTfInMinutes <= ONE_MIN * 2   => "5S"
                chartTfInMinutes <= ONE_MIN * 3   => "10S"
                chartTfInMinutes <= ONE_MIN * 5   => "15S"
                chartTfInMinutes <= ONE_MIN * 15  => "30S"
                chartTfInMinutes <= ONE_HOUR      => "1"
                chartTfInMinutes <  ONE_HOUR * 2  => "2"
                chartTfInMinutes <  ONE_HOUR * 4  => "3"
                chartTfInMinutes <  ONE_HOUR * 6  => "5"
                chartTfInMinutes <  ONE_HOUR * 12 => marketIs24Hours ? "10"  : "5"
                chartTfInMinutes <  ONE_DAY       => marketIs24Hours ? "15"  : "5"
                chartTfInMinutes <  ONE_WEEK      => marketIs24Hours ? "120" : "30"
                => "720"
        intrabars12  => PCtime.secondsToTfString(filterSmallTfs(timeframe.in_seconds() / int((48   * marketIs24HoursFactor))))
        intrabars24  => PCtime.secondsToTfString(filterSmallTfs(timeframe.in_seconds() / int((96   * marketIs24HoursFactor))))
        intrabars50  => PCtime.secondsToTfString(filterSmallTfs(timeframe.in_seconds() / int((200  * marketIs24HoursFactor))))
        intrabars100 => PCtime.secondsToTfString(filterSmallTfs(timeframe.in_seconds() / int((400  * marketIs24HoursFactor))))
        intrabars250 => PCtime.secondsToTfString(filterSmallTfs(timeframe.in_seconds() / int((1000 * marketIs24HoursFactor))))
        => "1S"


// @function                Returns statistics about analyzed intrabars and chart bars covered by calls to `request.security_lower_tf()`.
// @param intrabarValues    (float[]) The ID of a float array containing values fetched by a call to `request.security_lower_tf()`.
// @returns                 A 3-element tuple: ([(series int) intrabarsInChartBar, (series int) chartBarsCovered, (series float) avgIntrabars].
export ltfStats(float[] intrabarValues) =>
    // Qty of intrabars in the current chart bar.
    int intrabarsInChartBar = array.size(intrabarValues)
    // Chart bars where intrabar information is available.
    int chartBarsCovered = int(ta.cum(math.sign(intrabarsInChartBar)))
    // Avg qty of intrabars per chart bar.
    float avgIntrabars = nz(ta.cum(intrabarsInChartBar) / chartBarsCovered)
    [intrabarsInChartBar, chartBarsCovered, avgIntrabars]
//#endregion



//#region ———————————————————— Calculations 


// Get the LTF corresponding to user's selection.
//   NOTE
//      This is a good example of a case where we declare a variable with `var` to improve the script's execution time.
//      Declaring it this way calls the `ltf()` function only once, on the dataset's first bar.
//      The `ltf()` function has many string arguments and because it only needs to return a "simple string" for use in `request.security_lower_tf()`,
//      this entails that its value cannot change on further bars, so there is no need to execute it on them.
//      Because the function's code mostly manipulates strings, which the Pine runtime doesn't process as efficiently as numbers, this speeds up the script.
var string ltfString = ltf(ltfModeInput, LTF1, LTF2, LTF3, LTF4, LTF5, LTF6, LTF7, LTF8, LTF9, LTF10)

// Get array of `close` values for each intrabar in the chart's bar.
float[] intrabarCloses = request.security_lower_tf(syminfo.tickerid, ltfString, close)

// ———— Intrabar stats
[intrabars, chartBarsCovered, avgIntrabars] = ltfStats(intrabarCloses)
int chartBars = bar_index + 1
//#endregion



//#region ———————————————————— Visuals 


// Plots visible in the pane.
plot(avgIntrabars, "Average intrabars", color.silver, 6)
plot(intrabars,    "Intrabars",         color.blue,   2)

// Values visible in the Data Window and in the script's status line.
plot(chartBarsCovered,  "Chart bars covered", display = display.data_window + display.status_line)
plot(chartBars,         "Chart bars total",   display = display.data_window + display.status_line)

// Information box.
if showInfoBoxInput
    var table infoBox = table.new(infoBoxYPosInput + "_" + infoBoxXPosInput, 1, 1)
    string formattedLtf = PCtime.formattedNoOfPeriods(timeframe.in_seconds(ltfString) * 1000)
    string txt = str.format(TAB_TXT, formattedLtf, avgIntrabars,  chartBarsCovered, chartBars, chartBarsCovered / chartBars * 100)
    if barstate.isfirst
        table.cell(infoBox, 0, 0, txt, text_color = infoBoxTxtColorInput, text_size = infoBoxSizeInput, bgcolor = infoBoxColorInput)
    else if barstate.islast
        table.cell_set_text(infoBox, 0, 0, txt)        

// Error if no intrabars exist. 
if ta.cum(intrabars) == 0 and barstate.islast
    runtime.error(str.format(ERR_TXT, ltfString))
//#endregion

Overview

lower_tf chooses a lower timeframe for the chart based on a precision setting, either by how many chart bars should be covered or by the approximate number of intrabars per chart bar, bearing in mind the cap on analysable intrabars. An optional information box shows the timeframe used and the coverage. It draws nothing unless a calling script uses its functions.

Details

Published by

ivansoft on GitHub

Code credit

PineCoders, as written in the script's header

Draws

Library (no plots)

Markets

Any symbol

Timeframes

Any timeframe

Risk Notes

No repainting, lookahead or stacked entries were found in its code or README. That says nothing about how well it works: test it first.

Topics

pinescripttradingvew

Settings

The inputs you can change from the gear icon on the chart. Defaults are the author's.

SettingTypeDefaultVariable
Intrabar precisionstringLTF3ltfModeInput
Show information box booltrueshowInfoBoxInput
Size stringnormalinfoBoxSizeInput
↕stringbottominfoBoxYPosInput
↔stringleftinfoBoxXPosInput
infoBoxColorInputcolorGRAYinfoBoxColorInput
TcolorWHITEinfoBoxTxtColorInput
Third-party code. ForexR did not write, test or endorse this script, and the summary above was generated automatically from its code and README. Indicators describe the past, and a strategy's backtest can look better than live trading, especially when a script repaints. Check it in the Strategy Tester and on a demo account before you rely on it.

Similar Pine Scripts

261 stars

AIActivationFunctionsBipolarSigmoid is a Pine Script library that provides mathematical implementations of the bipolar sigmoid activation function and its derivatives for machine learning algorithms. It calculates bipolar sigmoid values bounded between -1 and

Library v5 AI / machine learning
Updated 4 years ago · None stated GitHub repository of AIActivationFunctionsBipolarSigmoid

KernelFunctions

by artificial-intelligence-edge
75 stars

KernelFunctions is a Pine Script v5 library that exports kernel weight functions for Nadaraya-Watson style estimation. It calculates a Rational Quadratic kernel, a Gaussian kernel based on a radial basis function, and a periodic kernel that models repeating be

Library v5
Updated 3 days ago · MIT GitHub repository of KernelFunctions

Ta

by nersent
29 stars

This Pine Script v5 library exports thin wrappers around built-in technical analysis functions. It covers moving averages, momentum measures such as RSI and CCI, volatility tools including ATR and standard deviation, range extremes, cross detection, and runnin

Library v5
Updated 11 months ago · Custom licence GitHub repository of Ta

Bands

by heyphat
26 stars

This library exports a Band type and functions that build a simple-moving-average basis with upper and lower envelopes from standard deviation. It classifies a source as above, below, or inside those envelopes, measures band width, and scales an imported z-sco

Library v6 Volatility & bandsMoving averages
Updated 2 months ago · AGPL-3.0 GitHub repository of Bands

Mylib

by ferranbt
21 stars

This script serves as a minimal utility library written in Pine Script v6. It provides an exported helper function that calculates the sum of two numeric arguments. As a reusable code library, it produces no visual plots, charts, or trading signals, and it con

Library v6
Updated 7 weeks ago · MPL-2.0 GitHub repository of Mylib

HLevel

by stupenkov
14 stars

HLevel is a Pine Script v5 utility library designed to manage horizontal price levels for cryptocurrency charts. It defines custom types for pivots and levels, along with methods to initialize, add, track, and expire price levels based on pivot high and pivot

Library v5
Updated 3 years ago · None stated GitHub repository of HLevel

More libraries

Related on ForexR

Trade Your Charts With a Regulated Broker

Compare brokers that connect to TradingView, with spreads, minimum deposits and leverage side by side.

Compare brokers