Search code examples
linepine-scriptpine-script-v5

Pinescript conditional line end/delete


I’m trying to create lines that auto plot at certain intervals using the line.new() function. So for example every new monthly open there will be lines plotted 5% and 10% above and beneath price. They’re then extended to the right indefinitely.

I then want to have the lines end once high/low has breached the line. I can’t seem to figure how to do this using the line.delete() function, although I doubt this is the correct path to take anyway due to the fact this deletes the entire line rather than just end it at breach point.

Due to the fact lines are extended indefinitely/until price has breached, there may be instances in which lines are never touched and are only removed once the 500 max line limit is reached. So I haven’t figured a way to use array references for lines to find a solution - and the 40 plot limit for pine plots isn’t really a sufficient amount of lines.

If this isn’t possible then just deleting the entire line upon breach is a backup option but I haven’t figure how to do this either!

Any help is much appreciated, thanks in advance!


Solution

  • You can use additional arrays to track the price values and their crossed state more easily. Each element of the arrays corresponds to the values associated with the same line. We add, remove or modify them based on whether a particular line's price value has been crossed or the line limit has been exceeded.

    //@version=5
    indicator("Monthly Interval Lines", overlay = true, max_lines_count = 500)
    
    var float[] interval_prices = array.new_float()
    var line[] interval_lines = array.new_line()
    var bool[] intervals_crossed = array.new_bool()
    
    new_month = timeframe.change("M")
    
    if new_month
        array.unshift(interval_lines, line.new(x1 = bar_index, y1 = open * 1.05, x2 = bar_index + 1, y2 = open * 1.05, extend = extend.right, color = color.green))
        array.unshift(interval_prices, open * 1.05)
        array.unshift(intervals_crossed, false)
        
        array.unshift(interval_lines, line.new(x1 = bar_index, y1 = open * 1.10, x2 = bar_index + 1, y2 = open * 1.10, extend = extend.right, color = color.green))
        array.unshift(interval_prices, open * 1.10)    
        array.unshift(intervals_crossed, false)
        
        array.unshift(interval_lines, line.new(x1 = bar_index, y1 = open * 0.95, x2 = bar_index + 1, y2 = open * 0.95, extend = extend.right, color = color.red))
        array.unshift(interval_prices, open * 0.95)
        array.unshift(intervals_crossed, false)
        
        array.unshift(interval_lines, line.new(x1 = bar_index, y1 = open * 0.90, x2 = bar_index + 1, y2 = open * 0.90, extend = extend.right, color = color.red))
        array.unshift(interval_prices, open * 0.90)
        array.unshift(intervals_crossed, false)
    
    size = array.size(intervals_crossed)
    
    if size > 0
        if size > 500
            for i = size - 1 to 500
                line.delete(array.pop(interval_lines))
                array.pop(intervals_crossed)
        
        size := array.size(intervals_crossed)
        
        for i = 0 to size - 1
            price_val = array.get(interval_prices, i)
            already_crossed = array.get(intervals_crossed, i)
            
            crossed_price_val = low < price_val and high > price_val
            gapped_price_val = (close[1] < price_val and open > price_val) or (close[1] > price_val and open < price_val)
            
            if not already_crossed and (crossed_price_val or gapped_price_val)
                array.set(intervals_crossed, i, true)
                interval_line = array.get(interval_lines, i)
                line.set_extend(interval_line, extend.none)
                line.set_x2(interval_line, bar_index)