7

I´m trying to create a simple plot with candlesticks. For that I get the data from Yahoo and plot it using the function candlestick2_ohlc. The goal is to export the image in a jpg file using.

This is the code what I´m using:

from pandas_datareader import data
import matplotlib.pyplot as plt
from mpl_finance import candlestick2_ohlc
import matplotlib.dates as mdates
import fix_yahoo_finance as yf
import datetime

start = datetime.date(2018, 1, 1)
end = datetime.date.today()
    
aapl = yf.download("AAPL",start,end) 
aapl.reset_index(inplace=True)

aapl['Date'] = aapl.index.map(mdates.date2num)

fig, ax = plt.subplots()
plt.xlabel("Date")
plt.ylabel("Price")

candlestick2_ohlc(ax, aapl.Open, aapl.High, aapl.Low, aapl.Close, width=1, colorup='g')
plt.savefig('my_figure.png')
plt.show()

My first question is: there is another simple way to do it? Could you please give me an example to work with finance data? I usually work with quantmod in R.

The second question is: In my example, there is no Date in the X axis. What can I do to show the plot with Dates in the X axis? I should transform the Date into a AX format but I don't know a simple way to do it.

Trenton McKinney
  • 56,955
  • 33
  • 144
  • 158
Alberto Aguilera
  • 311
  • 1
  • 5
  • 13
  • Possible duplicate of [how to plot ohlc candlestick with datetime in matplotlib?](https://stackoverflow.com/questions/36334665/how-to-plot-ohlc-candlestick-with-datetime-in-matplotlib) – Parfait Dec 10 '18 at 00:09
  • No, in my case I´m using Dates, no Intraday and I´m asking more thinks. thanks :) – Alberto Aguilera Dec 10 '18 at 08:04
  • I don't believe it matters the frequency, yours and dup question involves datetimes. Also what does *simple way to do it* mean? You have one plot line and 4-5 `plt` settings (typical of matplotlib solutions). – Parfait Dec 10 '18 at 15:00

4 Answers4

17

There are many ways of how plotting candlesticks in python using different package like:

  1. mplfinance
  2. plotly
  3. finplot
  4. etc.

You can also create your own specialized version of candlesticks using matplotlib package.

mplfinance Package

You can install the package using the following command:

pip install mplfinance

Then, you should use it as the following:

  1. Indices should be from DatetimeIndex format.
  2. The dataset should have the columns named: High, Open, Close and Low. (it's case-sensitive)
  3. (optional) if you want to show the volume, the Volume named column is required.

PS 1: You can create DatetimeIndex using pandas to_datetime method. PS 2: You can rename a column using rename method on dataframe.

Sample:

import pandas as pd
import mplfinance as mpf

df = pd.read_csv("<dataframe-path>", index_col=0)
mpf.plot(df, type='candle', style='yahoo', volume=True)

plotly Package

First you need to install the plotly package using:

pip install plotly

Then, you can plot the candle plots as easy as the following code:

import plotly.graph_objects as go

import pandas as pd
from datetime import datetime

df = pd.read_csv('your_file_address')

fig = go.Figure(data=[go.Candlestick(x=df['name_of_time_column'],
                open=df['name_of_open_column'],
                high=df['name_of_high_column'],
                low=df['name_of_low_column'],
                close=df['name_of_close_column'])])

fig.show()

finplot Package

You can install finplot package using the following command:

pip install finplot

then, it's really easy to build a candlestick plot.

Example:

import finplot as fplt
import pandas as pd
df = pd.read_csv("<data-path.csv>")

fplt.candlestick_ochl(df[['Open', 'Close', 'High', 'Low']])
fplt.show()
Mostafa Ghadimi
  • 5,883
  • 8
  • 64
  • 102
8

finplot has working dates:

import finplot as fplt
import yfinance
df = yfinance.download('AAPL')
fplt.candlestick_ochl(df[['Open', 'Close', 'High', 'Low']])
fplt.show()

finplot shows your dates

Not only does it show your dates, but also has many improvements (too many to list here).

Disclaimer: I dislike matplotlib's and plotly's API's (and performance and lack of functionality), so created finplot. Already it has 9% of the mpl_finance's pypi stars, so check it!

Jonas Byström
  • 25,316
  • 23
  • 100
  • 147
  • 1
    I have just updated (my answer)[https://stackoverflow.com/a/59256790/7310077], it would be a nice experience to try. I hope it helps. – Mostafa Ghadimi Sep 07 '20 at 23:13
  • 1
    Thanks @MostafaGhadimi! I try to emphasize ease of use and performance, which is why I made it in the first place. – Jonas Byström Sep 07 '20 at 23:33
  • 1
    Yeah. Thank you very much, Jonas. Yeah you're right, my upvote goes for you man. It is a really good answer. – Mostafa Ghadimi Sep 07 '20 at 23:34
  • Hi @JonasByström! I just installed finplot, and tried your example (litteraly copied your code). I get the following error: [IndexError: index 4 is out of bounds for axis 0 with size 4]. Did you ever encoutered this one? – mStudent Dec 25 '20 at 16:36
  • 1
    @the_drug Nope, sounds strange. Did you try any of the dozen included examples? Open an issue on [github](https://github.com/highfestiva/finplot/issues) if the problem remains. – Jonas Byström Dec 26 '20 at 00:22
  • @JonasByström i also like your library. from the first glimpse i got it seems to be easy and straight forward to use :) maybe you could write some kind of documentation for the 'clean API' you mention in your readmes. Guess that would make it a) a bit more professional and b) lower the entry hurdle. thanks for your work so far :) I'll start using it today and see how far I'll get ;) – 3.141592 Jan 13 '21 at 18:50
  • @3.141592 I use examples instead of documentation. The reason is that's how I personally prefer to learn. Good luck though! – Jonas Byström Jan 13 '21 at 19:47
  • @the_drug i got the same error, but here is the fix -- example should actually be fplt.candlestick_ochl(df[['Timestamp', 'Open', 'Close', 'High', 'Low']]) – OlDor Jan 27 '21 at 09:27
  • @OlDor could your `yfinance` module be older than 3 years? Before [this](https://github.com/ranaroussi/yfinance/commit/a1dfc6f1215b25bed4fb3444d0f58bb308f02188) fix possibly? – Jonas Byström Jan 27 '21 at 14:55
  • @JonasByström i didn't use yfinance, i have my own data_df – OlDor Jan 29 '21 at 06:37
  • @OlDor the_drug said he "litteraly copied [the] code." Sounds like you both exaggerated on either the "litteraly" or the "copied" part. ;) – Jonas Byström Jan 29 '21 at 07:37
3

Use Plotly and you can plot a candlestick chart with one line of code.

df[['Open', 'High', 'Low', 'Close']]['2018-01-01':'20XX-XX-XX'].iplot(kind="candle")

Before using plotly, you need install plotly and cufflinks with pip at your command line:

pip install plotly

pip install cufflinks

Also you need to import followings on the top of your Jupiter Notebook:

from plotly import __version__

import cufflinks as cf

from plotly.offline import download_plotlyjs, init_notebook_mode, plot, iplot

init_notebook_mode (connected=True)

cf.go_offline()
ejderuby
  • 710
  • 5
  • 21
2

You can do everthing with matplot (use Boxplot)

df = pdr.data.get_data_yahoo(ticker, start='2012-01-01', end='2012-10-10')
df = df[['Open', 'High', 'Low', 'Close']]

fig, ax1 = plt.subplots(figsize=(14,7), num='figure name')

ax1.set_title('box title')
ax1.yaxis.grid(True, linestyle='-', which='major', color='lightgrey', alpha=0.5)
ax1.xaxis.grid(True, linestyle='-', which='major', color='lightgrey', alpha=0.5)

bp = ax1.boxplot(df, patch_artist=True, labels=df.index.astype(str))

# green up, red down
for count_box in range(len(df.index)):
    if (df.iloc[count_box,0]-df.iloc[count_box,3])>=0:
       plt.setp(bp['boxes'][count_box], color='red')
    else:
       plt.setp(bp['boxes'][count_box], color='green')

 plt.xticks(rotation=30)
 plt.show() #or plt.savefig()
lux7
  • 1,600
  • 2
  • 18
  • 34
I value -u 2
  • 107
  • 1
  • 4
  • Getting the error: plt.setp(bp['boxes'][count_box], color='green') IndexError: list index out of range – holistic Jun 07 '21 at 15:54