how to use plotly lib for Financial Chart
import ccxt
from datetime import datetime
import pandas as pd
import numpy as np
import plotly.graph_objects as go
from plotly.subplots import make_subplots
import pandas_ta as ta
exchange = ccxt.binance({
'options': {
'adjustForTimeDifference': True,
},
})
def fetch(symbol: str, timeframe: str, limit: int):
print(f"Fetching {symbol} new bars for {datetime.now().isoformat()}")
bars = exchange.fetch_ohlcv(
symbol, timeframe=timeframe, limit=limit) # fetch ohlcv
df = pd.DataFrame(bars[:-1], columns=['timestamp',
'open', 'high', 'low', 'close', 'volume'])
df['timestamp'] = pd.to_datetime(df['timestamp'], unit='ms')
df = df.set_index(pd.DatetimeIndex(df.timestamp))
return df
BTC = fetch('BTC/USDT', '1h', 1000)
fig = go.Figure()
fig.add_trace(go.Candlestick(x=BTC.index,
open=BTC['open'],
high=BTC['high'],
low=BTC['low'],
close=BTC['close'],
showlegend=False))
fig.show()
fig.add_trace(go.Candlestick(
x=BTC.index,
open=BTC['open'], high=BTC['high'],
low=BTC['low'], close=BTC['close'],
increasing_line_color='cyan', decreasing_line_color='gray'
))
fig.update_layout(xaxis_rangeslider_visible=False)
fig.update_xaxes(rangebreaks=[dict(bounds=["sat", "mon"])])
BTC['sam15'] = ta.sma(BTC.close , 15)
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['sam15'],
opacity=0.7,
line=dict(color='Black', width=2),
name='sma'))
BTC.loc[BTC['sam15'] >= BTC['close'], 'upper_sma15'] = BTC['sam15']
BTC.loc[BTC['sam15'] < BTC['close'], 'lower_sma15'] = BTC['sam15']
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['upper_sma15'],
opacity=1,
line=dict(color='Lime', width=4),
name='upper_sma'))
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['lower_sma15'],
opacity=1,
line=dict(color='Maroon', width=4),
name='lower_sma'))
BTC['signal'] = np.where(
BTC['close'] > BTC['sam15'], 1, 0)
BTC['position'] = BTC['signal'].diff()
BTC['long'] = np.where(
(BTC['position']) == 1, BTC.close, np.NAN)
BTC['short'] = np.where(
(BTC['position']) == -1, BTC.close, np.NAN)
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['long'],
mode='markers',
marker=dict(color='DarkGreen', size=12,
opacity=1),
marker_symbol=5,
name='long signal'))
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['short'],
mode='markers',
marker=dict(color='MediumVioletRed', size=12,
opacity=1),
marker_symbol=6,
name='short signal'))
# first replace fig = go.Figure() replace
fig = make_subplots(rows=2, cols=1, shared_xaxes=True)
#add
colors = ['green' if row['open'] - row['close'] >= 0
else 'red' for index, row in BTC.iterrows()]
fig.add_trace(go.Bar(x=BTC.index,
y=BTC['volume'],
marker_color=colors
), row=2, col=1)
# add visible='legendonly'
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['short'],
mode='markers',
marker=dict(color='MediumVioletRed', size=12,
opacity=1),
marker_symbol=6,
name='short signal',
visible='legendonly'))
# { bollinger band
def SMA(data: str = 'BTC', src: str = 'close', length: int = 20): # sma for middle band
return data[src].rolling(window=length).mean()
def TP(data: str = 'BTC'): # hlc/3 (typical price)
return(data['high']+data['low']+data['close'])/3
def BOLU(data: str = "BTC", src: str = 'tp', length: int = 20, m: int = 2): # upperband
return SMA(data, src, 20)+((m)*data[src].rolling(window=length).std())
def BOLD(data: str = 'BTC', src: str = 'tp', length: int = 20, m: int = 2): # lower band
return SMA(data, 'close', 20)-((m)*data[src].rolling(window=length).std())
# }
# { use bollinger band functions to calculate bbband
BTC['middelband'] = SMA(BTC, 'close', 20)
BTC['tp'] = TP(BTC)
BTC['upperband'] = BOLU(BTC, 'tp')
BTC['lowerband'] = BOLD(BTC, 'tp')
# }
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['upperband'],
fill=None,
mode='lines',
line_color='rgba(0, 0, 255, 0.5)',
line=dict(width=2),
name='upperband',
visible='legendonly'))
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['lowerband'],
opacity=0.3,
fill='tonexty',
line=dict(width=2),
name='lowerband',
line_color='rgba(0, 0, 255, 0.5)',
mode='lines', fillcolor='rgba(0, 0, 255, 0.1)',
visible='legendonly'))
# { set condition in new dataframe
bulish = BTC[(BTC['in_sqz'] == False) & (
BTC['close'] > BTC['middelband'])]
not_bulish = BTC[BTC.index.isin(bulish.index)].index
# }
fig.add_traces(go.Candlestick(x=billish.index,
open=bulish['open'], high=bulish['high'],
low=bulish['low'], close=bulish['close'],
increasing_line_color='SpringGreen',
decreasing_line_color='DarkGreen',
name='Bulish momentum(+/-)'))
# { import the libraries
import ccxt
from datetime import datetime
import pandas as pd
import numpy as np
import plotly.graph_objects as go
from plotly.subplots import make_subplots
import pandas_ta as ta
# }
# { show all rows and column
pd.set_option('display.max_rows', None)
#pd.set_option('display.max_column', None)
# }
# { load exchange
exchange = ccxt.binance({
'options': {
'adjustForTimeDifference': True,
},
})
# }
# { load data as function
def fetch(symbol: str, timeframe: str, limit: int):
print(f"Fetching {symbol} new bars for {datetime.now().isoformat()}")
bars = exchange.fetch_ohlcv(
symbol, timeframe=timeframe, limit=limit) # fetch ohlcv
df = pd.DataFrame(bars[:-1], columns=['timestamp',
'open', 'high', 'low', 'close', 'volume'])
df['timestamp'] = pd.to_datetime(df['timestamp'], unit='ms')
df = df.set_index(pd.DatetimeIndex(df.timestamp))
return df
# }
# { bollinger band
def SMA(data: str = 'BTC', src: str = 'close', length: int = 20): # sma for middle band
return data[src].rolling(window=length).mean()
def TP(data: str = 'BTC'): # hlc/3 (typical price)
return(data['high']+data['low']+data['close'])/3
def BOLU(data: str = "BTC", src: str = 'tp', length: int = 20, m: int = 2): # upperband
return SMA(data, src, 20)+((m)*data[src].rolling(window=length).std())
def BOLD(data: str = 'BTC', src: str = 'tp', length: int = 20, m: int = 2): # lower band
return SMA(data, 'close', 20)-((m)*data[src].rolling(window=length).std())
# }
# { set the symbol for data function
BTC = fetch('BTC/USDT', '1h', 1000)
# }
# { use panda ta lib for calculate sma
BTC['sam15'] = ta.sma(BTC.close, 15)
# }
# { creat tow data frame for change sma color
BTC.loc[BTC['sam15'] >= BTC['close'], 'upper_sma15'] = BTC['sam15']
BTC.loc[BTC['sam15'] < BTC['close'], 'lower_sma15'] = BTC['sam15']
# }
# { use bollinger band functions to calculate bbband
BTC['middelband'] = SMA(BTC, 'close', 20)
BTC['tp'] = TP(BTC)
BTC['upperband'] = BOLU(BTC, 'tp')
BTC['lowerband'] = BOLD(BTC, 'tp')
# }
# { find cross for plot marker
BTC['signal'] = np.where(
BTC['close'] > BTC['sam15'], 1, 0)
BTC['position'] = BTC['signal'].diff()
BTC['long'] = np.where(
(BTC['position']) == 1, BTC.close, np.NAN)
BTC['short'] = np.where(
(BTC['position']) == -1, BTC.close, np.NAN)
# }
# { set condition in new dataframe
bulish = BTC[(BTC['close'] > BTC['middelband'])]
not_bulish = BTC[BTC.index.isin(bulish.index)].index
# }
# { plot the data
fig = make_subplots(rows=2, cols=1, shared_xaxes=True)
#fig = go.Figure()
fig.add_trace(go.Candlestick(x=BTC.index,
open=BTC['open'],
high=BTC['high'],
low=BTC['low'],
close=BTC['close'],
showlegend=False))
fig.add_traces(go.Candlestick(x=bulish.index,
open=bulish['open'], high=bulish['high'],
low=bulish['low'], close=bulish['close'],
increasing_line_color='SpringGreen',
decreasing_line_color='DarkGreen',
name='Bulish momentum(+/-)'))
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['upper_sma15'],
opacity=1,
line=dict(color='Lime', width=4),
name='upper_sma'))
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['lower_sma15'],
opacity=1,
line=dict(color='Maroon', width=4),
name='lower_sma'))
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['long'],
mode='markers',
marker=dict(color='DarkGreen', size=12,
opacity=1),
marker_symbol=5,
name='long signal'))
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['short'],
mode='markers',
marker=dict(color='MediumVioletRed', size=12,
opacity=1),
marker_symbol=6,
name='short signal',
visible='legendonly'))
colors = ['green' if row['open'] - row['close'] >= 0
else 'red' for index, row in BTC.iterrows()]
fig.add_trace(go.Bar(x=BTC.index,
y=BTC['volume'],
marker_color=colors
), row=2, col=1)
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['middelband'],
opacity=1,
line=dict(color='orange', width=2),
name='middelband'))
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['upperband'],
fill=None,
mode='lines',
line_color='rgba(0, 0, 255, 0.5)',
line=dict(width=2),
name='upperband'))
fig.add_trace(go.Scatter(x=BTC.index,
y=BTC['lowerband'],
opacity=0.3,
fill='tonexty',
line=dict(width=2),
name='lowerband',
line_color='rgba(0, 0, 255, 0.5)',
mode='lines', fillcolor='rgba(0, 0, 255, 0.1)'))
fig.show()
# }