Adding custom indicator
-
I have developed my first custom backtrader indicator class (in a separate file) which calculates resistance values. The first thing I do in the next() method of this indicator class is to get the previous 8 values of self.data and store them in an array named 'ltp', like so:
class supres(bt.Indicator): lines = ('support','resistance') params = (('n', 8),) def __init__(self): #converting n to a nearest even number if self.p.n%2 != 0: self.p.n += 1 def next(self): ltp = self.data.get(ago=0, size=self.p.n) print(ltp)
When I come to call the indicator in the init of my strategy, I pass in self.data[0]. But the self.data[0] doesn't seem to be available in the the indicator class. When I print out 'ltp' from the indicator class the array is empty.
Here is my strategy code for the init and main that isolates the problem:
import backtrader as bt import datetime from backtrader import indicators as ind import numpy as np from supres_ind import supres # Create strategy class TestStrategy(bt.Strategy): def __init__(self): # Keep a reference to the "close" line in the data[0] dataseries self.dataclose = self.datas[0].close #calls the indicator self.support = supres(self.datas[0])
and
if __name__ == '__main__': datapath = '../../data/raw_bitcoin_data_copy.csv' data = bt.feeds.BacktraderCSVData( dataname=datapath, fromdate=datetime.datetime(2017, 1, 1), todate=datetime.datetime(2017, 7, 1), adjclose=False) cerebro = bt.Cerebro() cerebro.adddata(data) cerebro.addstrategy(TestStrategy) cerebro.broker.setcash(100000.0) cerebro.addsizer(bt.sizers.SizerFix, stake=10) cerebro.broker.setcommission(0.001) #0.1% print('Starting Portfolio Value: %.2f' % cerebro.broker.getvalue()) cerebro.run() print('Final Portfolio Value: %.2f' % cerebro.broker.getvalue())
Do I have to add the indicator class to the cerebro engine somehow? And does the indicator have to be called with bt.ind prefix?
Here is the form of the data:
timestamp open high low close volume adj close 2017-01-01 973.37 1000 964.37 992.95 4421.502883 992.95 2017-01-02 992.96 1034.39 990.52 1011.45 7723.635752 1011.45 2017-01-03 1011.52 1036.99 1006.71 1020.67 8614.250058 1020.67 2017-01-04 1020.69 1147 1018 1130.3 16222.23027 1130.3 2017-01-05 1131.1 1175 880 1007 20438.58193 1007 2017-01-06 1007 1033.85 875.01 895.71 14262.50427 895.71
Cheers
-
@maxpaton said in Adding custom indicator:
When I come to call the indicator in the init of my strategy, I pass in self.data[0]. But the self.data[0] doesn't seem to be available in the the indicator class. When I print out 'ltp' from the indicator class the array is empty.
There is nothing telling the framework how many bars make up the lookback period. Neither you nor additional elements in your indicator (like a Moving Average) what the period will be. It cannot as such provide you with
n
bars of information in advance.Subclass your indicator from:
PeriodN
which already provides aperiod
parameter and will do it for you. -
@backtrader Got it now, thanks