Skip to content

Commit 271e030

Browse files
tight_layout support figure padding (issue #193)
1 parent a0cefdc commit 271e030

30 files changed

+936
-4
lines changed

examples/scratch_pad/dev_scale_padding.ipynb

Lines changed: 817 additions & 0 deletions
Large diffs are not rendered by default.
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
import pandas as pd
2+
import mplfinance as mpf
3+
4+
print('\nmpf.__version__=',mpf.__version__,'\n')
5+
6+
filename = '../../data/SP500_NOV2019_IDay.csv'
7+
8+
intraday = pd.read_csv(filename,index_col=0,parse_dates=True)
9+
intraday = intraday.drop('Volume',axis=1) # Volume is zero anyway for this intraday data set
10+
intraday.index.name = 'Date'
11+
intraday.shape
12+
intraday.head(3)
13+
intraday.tail(3)
14+
15+
iday = intraday.loc['2019-11-06 15:00':'2019-11-06 16:00',:]
16+
17+
print('len(iday)=',len(iday))
18+
19+
#----------------------------------------------------------------
20+
mpf.plot(iday,type='candle')
21+
22+
print('\n\nscale_padding=0.65')
23+
mpf.plot(iday,type='candle',scale_padding=0.65)
24+
#----------------------------------------------------------------
25+
26+
print('\n\ntight_layout=True')
27+
mpf.plot(iday,type='candle',tight_layout=True,block=False,title='Tight Layout')
28+
29+
print('\n\ntight_layout, and scale_padding=0.85')
30+
mpf.plot(iday,type='candle',tight_layout=True,scale_padding=0.85,title='Tight/Scale=0.85')
31+
32+
#----------------------------------------------------------------
33+
print('\n\nscale_padding=2.5')
34+
mpf.plot(iday,type='candle',scale_padding=2.5)
35+
36+
print('\n\ntight_layout, and scale_padding=0.25')
37+
mpf.plot(iday,type='candle',tight_layout=True,scale_padding=0.25)
38+
#----------------------------------------------------------------
39+
40+
# filename='../../data/SP500_NOV2019_Hist.csv'
41+
# df = pd.read_csv(filename,index_col=0,parse_dates=True)
42+
# df.index.name = 'Date'
43+
# df.shape
44+
# df.head(3)
45+
# df.tail(3)
46+
47+
# print('len(df)=',len(df))
48+
49+
# mpf.plot(df,type='candle')

src/mplfinance/_arg_validators.py

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -242,3 +242,18 @@ def _process_kwargs(kwargs, vkwargs):
242242

243243
def _valid_panel_id(panid):
244244
return panid in ['main','lower'] or (isinstance(panid,int) and panid >= 0 and panid < 10)
245+
246+
def _scale_padding_validator(value):
247+
if isinstance(value,(int,float)):
248+
return True
249+
elif isinstance(value,dict):
250+
valid_keys=('left','right','top','bottom')
251+
for key in value:
252+
if key not in valid_keys:
253+
raise ValueError('Invalid key "'+str(key)+'" found in `scale_padding` dict.')
254+
if not isinstance(value[key],(int,float)):
255+
raise ValueError('`scale_padding` dict contains non-number at key "'+str(key)+'"')
256+
return True
257+
else:
258+
raise ValueError('`scale_padding` kwarg must be a number, or dict of (left,right,top,bottom) numbers.')
259+
return False

src/mplfinance/_panels.py

Lines changed: 50 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -144,10 +144,57 @@ def _build_panels( figure, config ):
144144

145145
#print('panels=')
146146
#print(panels)
147+
148+
# TODO: Throughout this section, right_pad is intentionally *less*
149+
# than left_pad. This assumes that the y-axis labels are on
150+
# the left, which is true for many mpf_styles, but *not* all.
151+
# Ideally need to determine which side has the axis labels.
152+
# And keep in mind, if secondary_y is in effect, then both
153+
# sides can have axis labels.
154+
155+
left_pad = 0.18
156+
right_pad = 0.10
157+
top_pad = 0.12
158+
bot_pad = 0.18
159+
160+
scale_left = scale_right = scale_top = scale_bot = 1.0
161+
162+
scale_padding = config['scale_padding']
163+
if isinstance(scale_padding,dict):
164+
if 'left' in scale_padding: scale_left = scale_padding['left']
165+
if 'right' in scale_padding: scale_right = scale_padding['right']
166+
if 'top' in scale_padding: scale_top = scale_padding['top']
167+
if 'bottom' in scale_padding: scale_bot = scale_padding['bottom']
168+
else: # isinstance(scale_padding,(int,float):
169+
scale_left = scale_right = scale_top = scale_bot = scale_padding
170+
171+
if config['tight_layout']:
172+
right_pad *= 0.4
173+
top_pad *= 0.4
174+
scale_left *= 0.6
175+
scale_right *= 0.6
176+
scale_top *= 0.6
177+
scale_bot *= 0.6
178+
179+
left_pad *= scale_left
180+
right_pad *= scale_right
181+
top_pad *= scale_top
182+
bot_pad *= scale_bot
183+
184+
plot_height = 1.0 - (bot_pad + top_pad )
185+
plot_width = 1.0 - (left_pad + right_pad)
186+
187+
# print('scale_padding=',scale_padding)
188+
# print('left_pad =',left_pad)
189+
# print('right_pad=',right_pad)
190+
# print('top_pad =',top_pad)
191+
# print('bot_pad =',bot_pad)
192+
# print('plot_height =',plot_height)
193+
# print('plot_width =',plot_width)
147194

148195
psum = sum(pratios)
149196
for panid,size in enumerate(pratios):
150-
panels.at[panid,'height'] = 0.7 * size / psum
197+
panels.at[panid,'height'] = plot_height * size / psum
151198

152199
# Now create the Axes:
153200

@@ -157,9 +204,9 @@ def _build_panels( figure, config ):
157204
panels.at[panid,'lift'] = lift
158205
if panid == 0:
159206
# rect = [left, bottom, width, height]
160-
ax0 = figure.add_axes( [0.15, 0.18+lift, 0.70, height] )
207+
ax0 = figure.add_axes( [left_pad, bot_pad+lift, plot_width, height] )
161208
else:
162-
ax0 = figure.add_axes( [0.15, 0.18+lift, 0.70, height], sharex=panels.at[0,'axes'][0] )
209+
ax0 = figure.add_axes( [left_pad, bot_pad+lift, plot_width, height], sharex=panels.at[0,'axes'][0] )
163210
ax1 = ax0.twinx()
164211
ax1.grid(False)
165212
if config['saxbelow']: # issue#115 issuecomment-639446764

src/mplfinance/_version.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11

2-
version_info = (0, 12, 6, 'alpha', 1)
2+
version_info = (0, 12, 6, 'alpha', 2)
33

44
_specifier_ = {'alpha': 'a','beta': 'b','candidate': 'rc','final': ''}
55

src/mplfinance/plotting.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@
3232
from mplfinance._arg_validators import _kwarg_not_implemented, _bypass_kwarg_validation
3333
from mplfinance._arg_validators import _hlines_validator, _vlines_validator
3434
from mplfinance._arg_validators import _alines_validator, _tlines_validator
35+
from mplfinance._arg_validators import _scale_padding_validator
3536
from mplfinance._arg_validators import _valid_panel_id
3637

3738
from mplfinance._panels import _build_panels
@@ -237,6 +238,9 @@ def _valid_plot_kwargs():
237238

238239
'saxbelow' : { 'Default' : True, # Issue#115 Comment#639446764
239240
'Validator' : lambda value: isinstance(value,bool) },
241+
242+
'scale_padding' : { 'Default' : 1.0, # Issue#193
243+
'Validator' : lambda value: _scale_padding_validator(value) },
240244
}
241245

242246
_validate_vkwargs_dict(vkwargs)

tests/reference_images/addplot01.png

192 Bytes
Loading

tests/reference_images/addplot02.png

-504 Bytes
Loading

tests/reference_images/addplot03.png

-1.63 KB
Loading

tests/reference_images/addplot04.png

-1.03 KB
Loading

0 commit comments

Comments
 (0)