0

My intention is to draw a line connecting the last two highs (and lows).

For that, I need the bar count (index) of the past two highs. I use the barssince() function and don't know how to properly formulate an expression that compares the counter series to the current value of the counter (minus 2).

A series called high_low holds the values: A 1 for every high, a -1 for every low and a 0 for neither high nor low.

The highs and lows are counted in two "var int" variables. Now I would like to find the position of the 2nd recent high.

Lets assume the current counter value is 54, the last high happened at bar index 8 and the high before at bar index 25.

To find the most recent high, I can do:

high1_idx = ta.barssince(high_counter[1] == high_counter - 1)
// now high1_idx is 8

But how do I do it for the previous high?

In barssince() I need to compare the high_low series to a fixed value that hold the recent counter value decrement by 2. This does not work:

// high_counter is 54
high_counter_static = high_counter[0]
high2_idx = ta.barssince(high_counter == high_counter_static - 2) - 1
// high2_idx is supposed to be 25

I don't know how to do it. Apparently in pine-script it's not possible to convert the current value of the high_counter series to a "normal" int, it will always be a series int (see Converting series integer to integer in pinescript).

It works fine when I put the number into the code manually for debugging purposes:

high2_idx = ta.barssince(high_counter == 54 - 2) - 1
// high2_idx now is 25

My most recent idea is to "abuse" the input type as a workaround, but this will cause the entire series to be re-calculated on any new high or low. Edit: Apparently I have misunderstood the documentation and the nature about input variables. So this workaround idea does not work (just tried it).

Any better suggestions?

Complete code:

//@version=5
indicator("High Low Line Indicator")

pre  = input.int(7, "A", minval=1)
post = input.int(3, "P", minval=0)
scale = input.float(100, "S", minval=1)

delay_shift = post

// Low by bars
found_low_a = ta.lowest(low[1+delay_shift], pre) > low[delay_shift]
found_low_p = low[post] < ta.lowest(low, post)

// High by bars
found_high_a = ta.highest(high[1+delay_shift], pre) < high[delay_shift]
found_high_p = high[post] > ta.highest(high, post)

// If it's pre and post, then it's a real high or low
found_low = found_low_a and found_low_p
found_high = found_high_a and found_high_p

// Create the high low indicator and plot it for debug purposes
high_low = found_high ? 1 : found_low ? -1 : 0 
plot(high_low*scale, color = color.white, offset = -delay_shift)

var int low_counter = 0
var int high_counter = 0

if found_low
    low_counter += 1
if found_high
    high_counter += 1

// Calculate distance to recent high (works fine)
high1_idx = ta.barssince(high_counter[1] == high_counter - 1) + delay_shift
plot(high1_idx, color = color.green, offset = -delay_shift)

// Calculate distance to previous high (don't now how to compare)
high2_idx = ta.barssince(high_counter == high_counter[0] -2) + delay_shift -1
plot(high2_idx, color = color.yellow, offset = -delay_shift)
ChristophK
  • 733
  • 7
  • 20
  • 1
    Check out ta.valuewhen() or use an array – Bjorgum May 29 '22 at 21:26
  • I stumbled over ta.valuewhen() but didn't know how to combine it with my script. Just a second after reading your comment I knew how to apply it :-) Sometimes it's a good thing to get some distance to the code ... – ChristophK May 30 '22 at 16:27

0 Answers0