how to show more area at the far right side of the Ichimoku Cloud Chart
Opened this issue · 1 comments
Greeting!
I am a newbie in Python, and I greatly appreciate this brilliantly made built-in package for visualization of yfinance data.
I am learning and trying to plot the Ichimoku Cloud Chart, and found that the plot displayed would show with the x-axis limited at the latest data date, while the Ichimoku indicator actually would plot the cloud area 26days into future.
I tried to extend the x-axis using the xlim() function to extend 1 month into future, but the cloud still is not shown in the plot.
I have checked and make sure that in my calculations, the shift() function is applied to the calculation of the 3 lines, Leading Span A, Leading Span B, and Lagging Span. Thus I believe that there would be data to be plotted for the future date.
The first chart below is the plot generated from my broken code.
And the lower chart is a chart I got from a free online platform. I target to make my plot look more or less like this.
May I get help on how I can correctly plot the cloud for the Ichimoku chart?
Thanks in advance.
This is the chart plotted from my broken python code

This is the chart I got from a free online platform. I target to make my plot look more or less like this.

in case it is necessart, this is my broken code
# This allows multiple outputs from a single jupyter notebook cell:
from IPython.core.interactiveshell import InteractiveShell
InteractiveShell.ast_node_interactivity = "all"
import yfinance as yf
import pandas as pd
import mplfinance as mpf
import numpy as np
import datetime as dt
from datetime import timedelta, date
# for fixing
# Error: Cannot compare tz-naive and tz-aware datetime-like objects
import pytz
from dateutil.relativedelta import relativedelta
# Print mplfinance version for debugging
#print(f"mplfinance version: {mpf.__version__}")
def get_stock_data(stock_symbol, start, end):
# Fetch stock data
security = yf.Ticker(stock_symbol)
stock = security.history(interval='1d', start=start_date, end=end_date)
#stock = yf.download(stock_symbol, start=start_date, end=end_date)
if stock.empty:
raise ValueError(f"No data retrieved for symbol '{stock_symbol}' between {start_date} and {end_date}")
# Calculate Ichimoku components, default parameters = 9, 26, 52
# Tenkan-sen (Conversion Line): (9-period high + 9-period low)/2
high_9 = stock['High'].rolling(window=9).max()
low_9 = stock['Low'].rolling(window=9).min()
stock['Tenkan_sen'] = (high_9 + low_9) / 2
# Kijun-sen (Base Line): (26-period high + 26-period low)/2
high_26 = stock['High'].rolling(window=26).max()
low_26 = stock['Low'].rolling(window=26).min()
stock['Kijun_sen'] = (high_26 + low_26) / 2
# Senkou Span A (Leading Span A): (Conversion Line + Base Line)/2 shifted 26 periods forward
stock['Senkou_Span_A'] = ((stock['Tenkan_sen'] + stock['Kijun_sen']) / 2).shift(26)
# Senkou Span B (Leading Span B): (52-period high + 52-period low)/2 shifted 26 periods forward
high_52 = stock['High'].rolling(window=52).max()
low_52 = stock['Low'].rolling(window=52).min()
stock['Senkou_Span_B'] = ((high_52 + low_52) / 2).shift(26)
# Chikou Span (Lagging Span): Close price shifted 26 periods back
stock['Chikou_Span'] = stock['Close'].shift(-26)
# Calculate MACD, default parameter = 12, 26, 9
stock['EMA_12'] = stock['Close'].ewm(span=12, adjust=False).mean()
stock['EMA_26'] = stock['Close'].ewm(span=26, adjust=False).mean()
stock['MACD'] = stock['EMA_12'] - stock['EMA_26']
stock['Signal_Line'] = stock['MACD'].ewm(span=9, adjust=False).mean()
stock['MACD_Hist'] = stock['MACD'] - stock['Signal_Line']
# Calculate RSI, default 14days RSI vs 5days SMA
delta = stock['Close'].diff()
gain = (delta.where(delta > 0, 0)).rolling(window=14).mean()
loss = (-delta.where(delta < 0, 0)).rolling(window=14).mean()
rs = gain / loss
stock['RSI'] = 100 - (100 / (1 + rs))
return stock
def plot_ichimoku_with_indicators(stock_symbol, data):
# Prepare the data for mplfinance (OHLC format)
ohlc_data = data[['Open', 'High', 'Low', 'Close', 'Volume']].copy()
# Debugging
print("ohlc_data head:\n", ohlc_data.head())
print("ohlc_data columns:", ohlc_data.columns.tolist())
print("Volume NaN count in ohlc_data:", ohlc_data['Volume'].isna().sum())
# Define additional plots for Ichimoku lines
ichimoku_lines = [
mpf.make_addplot(data['Tenkan_sen'], color='red', label='Tenkan-sen'),
mpf.make_addplot(data['Kijun_sen'], color='blue', label='Kijun-sen'),
mpf.make_addplot(data['Senkou_Span_A'], color='yellow', label='Senkou_Span_A'),
mpf.make_addplot(data['Senkou_Span_B'], color='purple', label='Senkou_Span_B'),
mpf.make_addplot(data['Chikou_Span'], color='black', label='Chikou Span'),
]
# Define the fill_between Senkou_Span_A and Senkou_Span_B for the cloud directly in the plot call
cloud_fill = [dict(y1=data['Senkou_Span_A'].values, y2=data['Senkou_Span_B'].values, where=data['Senkou_Span_A'] >= data['Senkou_Span_B'], alpha=0.3, color='green'),
dict(y1=data['Senkou_Span_A'].values, y2=data['Senkou_Span_B'].values, where=data['Senkou_Span_A'] < data['Senkou_Span_B'], alpha=0.3, color='red')]
# Volume = True in mpf.plot(), being panel = 1
# Define MACD panel
macd_plots = [
mpf.make_addplot(data['MACD'], color='blue', label='MACD', ylabel='MACD', y_on_right=False, panel=2, title="MACD"),
mpf.make_addplot(data['Signal_Line'], color='orange', label='Signal Line', panel=2),
mpf.make_addplot(data['MACD_Hist'], type='bar', color='gray', alpha=0.5, label='Histogram', panel=2),
mpf.make_addplot(pd.Series(0, index=data.index), color='black', linestyle='--', panel=2, width=0.5)
]
# Define RSI panel
rsi_plots = [
mpf.make_addplot(data['RSI'], color='blue', label='RSI', ylabel='RSI', y_on_right=False, panel=3, title="RSI"),
mpf.make_addplot(pd.Series(70, index=data.index), color='red', linestyle='--', panel=3, width=0.5),
mpf.make_addplot(pd.Series(30, index=data.index), color='green', linestyle='--', panel=3, width=0.5)
]
all_plots = ichimoku_lines + macd_plots + rsi_plots
# Plot using mplfinance
mpf.plot(ohlc_data,
type='hollow_candle', # Use candlestick chart, hollow
style='yahoo', # Yahoo-style coloring
title=f'Ichimoku Cloud Chart - {stock_symbol}',
addplot=all_plots,
volume=True, # panel = 1
panel_ratios=(3, 1, 1, 1), # Adjust panel sizes
fill_between=cloud_fill, # Add cloud fill for Ichimoku
ylabel='Price',
ylabel_lower='Volume',
#y_on_right=False,
xlim=(start_date, xlim_end),
figscale=1.5,
tight_layout=True,
)
# Example usage
if __name__ == "__main__":
#Set parameters
#ask suer for stock symbol
stock_symbol = input("Please enter the stock symbol: ")
start_date = dt.datetime(date.today().year - 1, date.today().month, date.today().day, tzinfo=pytz.UTC)
end_date = dt.datetime(date.today().year, date.today().month, date.today().day, tzinfo=pytz.UTC)
xlim_end = dt.datetime.today().replace(tzinfo=pytz.UTC) + relativedelta(months=1)
# Get data and plot
try:
ichimoku_data = get_stock_data(stock_symbol, start_date, end_date)
if ichimoku_data.empty:
raise ValueError("No data returned for the specified stock symbol.")
plot_ichimoku_with_indicators(stock_symbol, ichimoku_data)
except Exception as e:
print(f"Error: {str(e)}")
# Requirements:
# pip install yfinance pandas mplfinance numpy #