Auto-Fibonacci Tool
This lesson breaks down the AUTO-FIBONACCI tool created by the TradingView developers. I show how to adapt the Pine Script source code from the inbuilt tool to customize it for your own purposes.
Check out my other free lessons!Source Code
// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/ // © ZenAndTheArtOfTrading / PineScriptMastery.com // @version=5 indicator("Auto-Fib", overlay=true) // Get user input var devTooltip = "Deviation is a multiplier that affects how much the price should deviate from the previous pivot in order for the bar to become a new pivot." var depthTooltip = "The minimum number of bars that will be taken into account when calculating the indicator." threshold_multiplier = input.float(title="Deviation", defval=3, minval=0, tooltip=devTooltip) depth = input.int(title="Depth", defval=10, minval=1, tooltip=depthTooltip) reverse = input.bool(title="Reverse", defval=false, tooltip="Flips the fibonacci levels around.") extendLeft = input.bool(title="Extend Left | Extend Right", defval=false, inline="Extend Lines") extendRight = input.bool(title="", defval=false, inline="Extend Lines") prices = input.bool(title="Show Prices", defval=false) deleteLastLine = input.bool(title="Delete Last Line", defval=true) levels = input.bool(title="Show Levels", defval=true, inline="Levels") levelsFormat = input.string(title="", defval="Values", options=["Values", "Percent"], inline="Levels") labelsPosition = input.string(title="Labels Position", defval="Left", options=["Left", "Right"]) backgroundTransparency = input.int(title="Background Transparency", defval=85, minval=0, maxval=100) // Check extending parameter var extending = extend.none if extendLeft and extendRight extending := extend.both if extendLeft and not extendRight extending := extend.left if not extendLeft and extendRight extending := extend.right // Calculate deviation threshold for identifying major swings dev_threshold = ta.atr(10) / close * 100 * threshold_multiplier // Prepare pivot variables var line lineLast = na var int iLast = 0 var int iPrev = 0 var float pLast = 0 var isHighLast = false // Otherwise the last pivot is a low pivot // Custom function for detecting pivot points pivots(src, length, isHigh) => l2 = length * 2 c = nz(src[length]) ok = true for i = 0 to l2 if isHigh and src[i] > c ok := false if not isHigh and src[i] < c ok := false if ok [bar_index[length], c] else [int(na), float(na)] // Get bar index & price high/low for current pivots [iH, pH] = pivots(high, depth / 2, true) [iL, pL] = pivots(low, depth / 2, false) // Custom function for calculating price deviation calc_dev(base_price, price) => 100 * (price - base_price) / price // Custom function for detecting pivots that meet our deviation criteria pivotFound(dev, isHigh, index, price) => if isHighLast == isHigh and not na(lineLast) // New pivot in same direction as last, so update line (ie. trend-continuation) if isHighLast ? price > pLast : price < pLast line.set_xy2(lineLast, index, price) [lineLast, isHighLast] else [line(na), bool(na)] // No valid pivot detected, return nothing else // Reverse the trend/pivot direction (or create the very first line if lineLast is na) if math.abs(dev) > dev_threshold // Price move is significant - create a new line between the pivot points id = line.new(iLast, pLast, index, price, color=color.gray, width=1, style=line.style_dashed) [id, isHigh] else [line(na), bool(na)] // If bar index for current pivot high is not NA (ie. we have a new pivot): if not na(iH) dev = calc_dev(pLast, pH) // Calculate the deviation from last pivot [id, isHigh] = pivotFound(dev, true, iH, pH) if not na(id) // If the line has been updated, update price values and delete previous line if id != lineLast and deleteLastLine line.delete(lineLast) lineLast := id isHighLast := isHigh iPrev := iLast iLast := iH pLast := pH else if not na(iL) // If bar index for current pivot low is not NA (ie. we have a new pivot): dev = calc_dev(pLast, pL) // Calculate the deviation from last pivot [id, isHigh] = pivotFound(dev, false, iL, pL) if not na(id) // If the line has been updated, update price values and delete previous line if id != lineLast and deleteLastLine line.delete(lineLast) lineLast := id isHighLast := isHigh iPrev := iLast iLast := iL pLast := pL // Draw fibonacci level as a line and return the line object ID draw_fib_line(price, col) => var id = line.new(iLast, price, bar_index, price, color=col, width=1, extend=extending) if not na(lineLast) line.set_xy1(id, line.get_x1(lineLast), price) line.set_xy2(id, line.get_x2(lineLast), price) id // Draw fibonacci labels draw_label(price, txt, txtColor) => x = labelsPosition == "Left" ? line.get_x1(lineLast) : not extendRight ? line.get_x2(lineLast) : bar_index labelStyle = labelsPosition == "Left" ? label.style_label_right : label.style_label_left align = labelsPosition == "Left" ? text.align_right : text.align_left labelsAlignStrLeft = txt + '\n \n' labelsAlignStrRight = ' ' + txt + '\n \n' labelsAlignStr = labelsPosition == "Left" ? labelsAlignStrLeft : labelsAlignStrRight var id = label.new(x=x, y=price, text=labelsAlignStr, textcolor=txtColor, style=labelStyle, textalign=align, color=#00000000) label.set_xy(id, x, price) label.set_text(id, labelsAlignStr) label.set_textcolor(id, txtColor) // Format the given string format(txt) => " (" + str.tostring(txt, "#.####") + ")" // Return the formatted label text for Fibonacci levels label_txt(level, price) => l = levelsFormat == "Values" ? str.tostring(level) : str.tostring(level * 100) + "%" (levels ? l : "") + (prices ? format(price) : "") // Returns true if price is crossing the given fib level crossing_level(price, fib) => (fib > price and fib < price[1]) or (fib < price and fib > price[1]) // Get starting and ending high/low price of the current pivot (for calculating fib levels) startPrice = reverse ? line.get_y1(lineLast) : pLast endPrice = reverse ? pLast : line.get_y1(lineLast) // Calculate price difference between high and low iHL = startPrice > endPrice diff = (iHL ? -1 : 1) * math.abs(startPrice - endPrice) // Process the given fib level (calculate fib, draw line & label, detect alerts, fill bgcolor between last fib) processLevel(show, value, colorL, lineIdOther) => if show fibPrice = startPrice + diff * value lineId = draw_fib_line(fibPrice, colorL) draw_label(fibPrice, label_txt(value, fibPrice), colorL) if crossing_level(close, fibPrice) // Trigger alert if price is crossing this fib level alert("Autofib: " + syminfo.ticker + " crossing level " + str.tostring(value)) if not na(lineIdOther) // Fill background color between each fib level linefill.new(lineId, lineIdOther, color=color.new(colorL, backgroundTransparency)) lineId else lineIdOther //{============================================================================= var g_fibs = "Fibonacci Levels" // Get Fibonacci level user inputs show_0 = input(true, "", inline = "Level0", group=g_fibs) value_0 = input(0, "", inline = "Level0", group=g_fibs) color_0 = input(#787b86, "", inline = "Level0", group=g_fibs) //------------------------------------------------------------------------------ show_0_236 = input(true, "", inline = "Level0", group=g_fibs) value_0_236 = input(0.236, "", inline = "Level0", group=g_fibs) color_0_236 = input(#f44336, "", inline = "Level0", group=g_fibs) //------------------------------------------------------------------------------ show_0_382 = input(true, "", inline = "Level1", group=g_fibs) value_0_382 = input(0.382, "", inline = "Level1", group=g_fibs) color_0_382 = input(#81c784, "", inline = "Level1", group=g_fibs) //------------------------------------------------------------------------------ show_0_5 = input(true, "", inline = "Level1", group=g_fibs) value_0_5 = input(0.5, "", inline = "Level1", group=g_fibs) color_0_5 = input(#4caf50, "", inline = "Level1", group=g_fibs) //------------------------------------------------------------------------------ show_0_618 = input(true, "", inline = "Level2", group=g_fibs) value_0_618 = input(0.618, "", inline = "Level2", group=g_fibs) color_0_618 = input(#009688, "", inline = "Level2", group=g_fibs) //------------------------------------------------------------------------------ show_0_65 = input(false, "", inline = "Level2", group=g_fibs) value_0_65 = input(0.65, "", inline = "Level2", group=g_fibs) color_0_65 = input(#009688, "", inline = "Level2", group=g_fibs) //------------------------------------------------------------------------------ show_0_786 = input(true, "", inline = "Level3", group=g_fibs) value_0_786 = input(0.786, "", inline = "Level3", group=g_fibs) color_0_786 = input(#64b5f6, "", inline = "Level3", group=g_fibs) //------------------------------------------------------------------------------ show_1 = input(true, "", inline = "Level3", group=g_fibs) value_1 = input(1, "", inline = "Level3", group=g_fibs) color_1 = input(#787b86, "", inline = "Level3", group=g_fibs) //------------------------------------------------------------------------------ show_1_272 = input(false, "", inline = "Level4", group=g_fibs) value_1_272 = input(1.272, "", inline = "Level4", group=g_fibs) color_1_272 = input(#81c784, "", inline = "Level4", group=g_fibs) //------------------------------------------------------------------------------ show_1_414 = input(false, "", inline = "Level4", group=g_fibs) value_1_414 = input(1.414, "", inline = "Level4", group=g_fibs) color_1_414 = input(#f44336, "", inline = "Level4", group=g_fibs) //------------------------------------------------------------------------------ show_1_618 = input(false, "", inline = "Level5", group=g_fibs) value_1_618 = input(1.618, "", inline = "Level5", group=g_fibs) color_1_618 = input(#2196f3, "", inline = "Level5", group=g_fibs) //------------------------------------------------------------------------------ show_1_65 = input(false, "", inline = "Level5", group=g_fibs) value_1_65 = input(1.65, "", inline = "Level5", group=g_fibs) color_1_65 = input(#2196f3, "", inline = "Level5", group=g_fibs) //------------------------------------------------------------------------------ show_2_618 = input(false, "", inline = "Level6", group=g_fibs) value_2_618 = input(2.618, "", inline = "Level6", group=g_fibs) color_2_618 = input(#f44336, "", inline = "Level6", group=g_fibs) //------------------------------------------------------------------------------ show_2_65 = input(false, "", inline = "Level6", group=g_fibs) value_2_65 = input(2.65, "", inline = "Level6", group=g_fibs) color_2_65 = input(#f44336, "", inline = "Level6", group=g_fibs) //------------------------------------------------------------------------------ show_3_618 = input(false, "", inline = "Level7", group=g_fibs) value_3_618 = input(3.618, "", inline = "Level7", group=g_fibs) color_3_618 = input(#9c27b0, "", inline = "Level7", group=g_fibs) //------------------------------------------------------------------------------ show_3_65 = input(false, "", inline = "Level7", group=g_fibs) value_3_65 = input(3.65, "", inline = "Level7", group=g_fibs) color_3_65 = input(#9c27b0, "", inline = "Level7", group=g_fibs) //------------------------------------------------------------------------------ show_4_236 = input(false, "", inline = "Level8", group=g_fibs) value_4_236 = input(4.236, "", inline = "Level8", group=g_fibs) color_4_236 = input(#e91e63, "", inline = "Level8", group=g_fibs) //------------------------------------------------------------------------------ show_4_618 = input(false, "", inline = "Level8", group=g_fibs) value_4_618 = input(4.618, "", inline = "Level8", group=g_fibs) color_4_618 = input(#81c784, "", inline = "Level8", group=g_fibs) //------------------------------------------------------------------------------ show_neg_0_236 = input(false, "", inline = "Level9", group=g_fibs) value_neg_0_236 = input(-0.236, "", inline = "Level9", group=g_fibs) color_neg_0_236 = input(#f44336, "", inline = "Level9", group=g_fibs) //------------------------------------------------------------------------------ show_neg_0_382 = input(false, "", inline = "Level9", group=g_fibs) value_neg_0_382 = input(-0.382, "", inline = "Level9", group=g_fibs) color_neg_0_382 = input(#81c784, "", inline = "Level9", group=g_fibs) //------------------------------------------------------------------------------ show_neg_0_618 = input(false, "", inline = "Level10", group=g_fibs) value_neg_0_618 = input(-0.618, "", inline = "Level10", group=g_fibs) color_neg_0_618 = input(#009688, "", inline = "Level10", group=g_fibs) //------------------------------------------------------------------------------ show_neg_0_65 = input(false, "", inline = "Level10", group=g_fibs) value_neg_0_65 = input(-0.65, "", inline = "Level10", group=g_fibs) color_neg_0_65 = input(#009688, "", inline = "Level10", group=g_fibs) //-----------------------------------------------------------------------------} //{============================================================================= // Process each fibonacci level //============================================================================== lineId0 = processLevel(show_neg_0_65, value_neg_0_65, color_neg_0_65, line(na)) lineId1 = processLevel(show_neg_0_618, value_neg_0_618, color_neg_0_618, lineId0) lineId2 = processLevel(show_neg_0_382, value_neg_0_382, color_neg_0_382, lineId1) lineId3 = processLevel(show_neg_0_236, value_neg_0_236, color_neg_0_236, lineId2) lineId4 = processLevel(show_0, value_0, color_0, lineId3) lineId5 = processLevel(show_0_236, value_0_236, color_0_236, lineId4) lineId6 = processLevel(show_0_382, value_0_382, color_0_382, lineId5) lineId7 = processLevel(show_0_5, value_0_5, color_0_5, lineId6) lineId8 = processLevel(show_0_618, value_0_618, color_0_618, lineId7) lineId9 = processLevel(show_0_65, value_0_65, color_0_65, lineId8) lineId10 = processLevel(show_0_786, value_0_786, color_0_786, lineId9) lineId11 = processLevel(show_1, value_1, color_1, lineId10) lineId12 = processLevel(show_1_272, value_1_272, color_1_272, lineId11) lineId13 = processLevel(show_1_414, value_1_414, color_1_414, lineId12) lineId14 = processLevel(show_1_618, value_1_618, color_1_618, lineId13) lineId15 = processLevel(show_1_65, value_1_65, color_1_65, lineId14) lineId16 = processLevel(show_2_618, value_2_618, color_2_618, lineId15) lineId17 = processLevel(show_2_65, value_2_65, color_2_65, lineId16) lineId18 = processLevel(show_3_618, value_3_618, color_3_618, lineId17) lineId19 = processLevel(show_3_65, value_3_65, color_3_65, lineId18) lineId20 = processLevel(show_4_236, value_4_236, color_4_236, lineId19) lineId21 = processLevel(show_4_618, value_4_618, color_4_618, lineId20) //-----------------------------------------------------------------------------}