Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 9246445

Browse files
committed
add tight_layout functionality
1 parent 635cf1f commit 9246445

5 files changed

Lines changed: 435 additions & 0 deletions

File tree

Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
2+
import matplotlib.pyplot as plt
3+
4+
5+
import random
6+
fontsizes = [8, 16, 24, 32]
7+
def example_plot(ax):
8+
ax.plot([1, 2])
9+
ax.set_xlabel('x-label', fontsize=random.choice(fontsizes))
10+
ax.set_ylabel('y-label', fontsize=random.choice(fontsizes))
11+
ax.set_title('Title', fontsize=random.choice(fontsizes))
12+
13+
if 1:
14+
fig, ax = plt.subplots()
15+
example_plot(ax)
16+
plt.tight_layout()
17+
18+
fig, ((ax1, ax2), (ax3, ax4)) = plt.subplots(nrows=2, ncols=2)
19+
example_plot(ax1)
20+
example_plot(ax2)
21+
example_plot(ax3)
22+
example_plot(ax4)
23+
plt.tight_layout()
24+
25+
fig, (ax1, ax2) = plt.subplots(nrows=2, ncols=1)
26+
example_plot(ax1)
27+
example_plot(ax2)
28+
plt.tight_layout()
29+
30+
fig, (ax1, ax2) = plt.subplots(nrows=1, ncols=2)
31+
example_plot(ax1)
32+
example_plot(ax2)
33+
plt.tight_layout()
34+
35+
fig, axes = plt.subplots(nrows=3, ncols=3)
36+
for row in axes:
37+
for ax in row:
38+
example_plot(ax)
39+
plt.tight_layout()
40+
41+
42+
fig = plt.figure()
43+
44+
ax1 = plt.subplot(221)
45+
ax2 = plt.subplot(223)
46+
ax3 = plt.subplot(122)
47+
48+
example_plot(ax1)
49+
example_plot(ax2)
50+
example_plot(ax3)
51+
52+
plt.tight_layout()
53+
54+
55+
fig = plt.figure()
56+
57+
ax1 = plt.subplot2grid((3, 3), (0, 0))
58+
ax2 = plt.subplot2grid((3, 3), (0, 1), colspan=2)
59+
ax3 = plt.subplot2grid((3, 3), (1, 0), colspan=2, rowspan=2)
60+
ax4 = plt.subplot2grid((3, 3), (1, 2), rowspan=2)
61+
62+
example_plot(ax1)
63+
example_plot(ax2)
64+
example_plot(ax3)
65+
example_plot(ax4)
66+
67+
plt.tight_layout()
68+
69+
plt.show()
70+
71+
72+
fig = plt.figure()
73+
74+
import matplotlib.gridspec as gridspec
75+
76+
gs1 = gridspec.GridSpec(3, 1)
77+
ax1 = fig.add_subplot(gs1[0])
78+
ax2 = fig.add_subplot(gs1[1])
79+
ax3 = fig.add_subplot(gs1[2])
80+
81+
example_plot(ax1)
82+
example_plot(ax2)
83+
example_plot(ax3)
84+
85+
gs1.tight_layout(fig, rect=[None, None, 0.45, None])
86+
87+
gs2 = gridspec.GridSpec(2, 1)
88+
ax4 = fig.add_subplot(gs2[0])
89+
ax5 = fig.add_subplot(gs2[1])
90+
91+
example_plot(ax4)
92+
example_plot(ax5)
93+
94+
gs2.tight_layout(fig, rect=[0.45, None, None, None])
95+
96+
# now match the top and bottom of two gridspecs.
97+
top = min(gs1.top, gs2.top)
98+
bottom = max(gs1.bottom, gs2.bottom)
99+
100+
gs1.update(top=top, bottom=bottom)
101+
gs2.update(top=top, bottom=bottom)
102+
103+
plt.show()
104+
105+
106+

lib/matplotlib/figure.py

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1295,6 +1295,65 @@ def get_tightbbox(self, renderer):
12951295
return bbox_inches
12961296

12971297

1298+
def tight_layout(self, renderer=None, pad=1.2, h_pad=None, w_pad=None):
1299+
"""Adjust subplot parameters to give specified padding.
1300+
1301+
Parameters
1302+
----------
1303+
pad : float
1304+
padding between the figure edge and the edges of subplots, as a fraction of the font-size.
1305+
h_pad, w_pad : float
1306+
padding (height/width) between edges of adjacent subplots.
1307+
Defaults to `pad_inches`.
1308+
"""
1309+
1310+
from tight_layout import auto_adjust_subplotpars, get_renderer
1311+
1312+
if renderer is None:
1313+
renderer = get_renderer(self)
1314+
1315+
subplot_list = []
1316+
nrows_list = []
1317+
ncols_list = []
1318+
1319+
for ax in self.axes:
1320+
if not isinstance(ax, SubplotBase): continue
1321+
subplot_list.append(ax)
1322+
1323+
myrows, mycols, _, _ = ax.get_subplotspec().get_geometry()
1324+
nrows_list.append(myrows)
1325+
ncols_list.append(mycols)
1326+
1327+
max_nrows = max(nrows_list)
1328+
max_ncols = max(ncols_list)
1329+
1330+
num1num2_list = []
1331+
for ax in subplot_list:
1332+
rows, cols, num1, num2 = ax.get_subplotspec().get_geometry()
1333+
div_row, mod_row = divmod(max_nrows, rows)
1334+
div_col, mod_col = divmod(max_ncols, cols)
1335+
if (mod_row != 0) or (mod_col != 0):
1336+
raise RuntimeError("")
1337+
1338+
rowNum1, colNum1 = divmod(num1, cols)
1339+
if num2 is None:
1340+
rowNum2, colNum2 = rowNum1, colNum1
1341+
else:
1342+
rowNum2, colNum2 = divmod(num2, cols)
1343+
1344+
num1num2_list.append((rowNum1*div_row*max_ncols + colNum1*div_col,
1345+
((rowNum2+1)*div_row-1)*max_ncols + (colNum2+1)*div_col-1))
1346+
1347+
1348+
kwargs = auto_adjust_subplotpars(self, renderer,
1349+
nrows_ncols=(max_nrows, max_ncols),
1350+
num1num2_list=num1num2_list,
1351+
subplot_list=subplot_list,
1352+
pad=pad, h_pad=h_pad, w_pad=w_pad)
1353+
1354+
self.subplots_adjust(**kwargs)
1355+
1356+
12981357

12991358
def figaspect(arg):
13001359
"""

lib/matplotlib/gridspec.py

Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -263,6 +263,73 @@ def get_subplot_params(self, fig=None):
263263

264264
return subplotpars
265265

266+
def locally_modified_subplot_params(self):
267+
return [k for k in self._AllowedKeys if getattr(self, k)]
268+
269+
270+
def tight_layout(self, fig, renderer=None, pad=1.2, h_pad=None, w_pad=None, rect=None):
271+
"""Adjust subplot parameters to give specified padding.
272+
273+
Parameters
274+
----------
275+
pad : float
276+
padding between the figure edge and the edges of subplots, as a fraction of the font-size.
277+
h_pad, w_pad : float
278+
padding (height/width) between edges of adjacent subplots.
279+
Defaults to `pad_inches`.
280+
"""
281+
282+
from tight_layout import auto_adjust_subplotpars, get_renderer
283+
284+
if renderer is None:
285+
renderer = get_renderer(fig)
286+
287+
subplot_list = []
288+
num1num2_list = []
289+
290+
for ax in fig.axes:
291+
if hasattr(ax, "get_subplotspec"):
292+
subplotspec = ax.get_subplotspec()
293+
if subplotspec.get_gridspec() == self:
294+
subplot_list.append(ax)
295+
_, _, num1, num2 = subplotspec.get_geometry()
296+
num1num2_list.append((num1, num2))
297+
298+
299+
kwargs = auto_adjust_subplotpars(fig, renderer,
300+
nrows_ncols=self.get_geometry(),
301+
num1num2_list=num1num2_list,
302+
subplot_list=subplot_list,
303+
pad=pad, h_pad=h_pad, w_pad=w_pad)
304+
305+
if rect is not None:
306+
# if rect is given, the whole subplots area (including
307+
# labels) will fit into the rect instead of the
308+
# figure. Note that the rect argument of
309+
# *auto_adjust_subplotpars* specify the area that will be
310+
# covered by the total area of axes.bbox. Thus we call
311+
# auto_adjust_subplotpars twice, where the second run
312+
# with adjusted rect parameters.
313+
314+
left, bottom, right, top = rect
315+
if left is not None: left += kwargs["left"]
316+
if bottom is not None: bottom += kwargs["bottom"]
317+
if right is not None: right -= (1 - kwargs["right"])
318+
if top is not None: top -= (1 - kwargs["top"])
319+
320+
#if h_pad is None: h_pad = pad
321+
#if w_pad is None: w_pad = pad
322+
323+
kwargs = auto_adjust_subplotpars(fig, renderer,
324+
nrows_ncols=self.get_geometry(),
325+
num1num2_list=num1num2_list,
326+
subplot_list=subplot_list,
327+
pad=pad, h_pad=h_pad, w_pad=w_pad,
328+
rect=(left, bottom, right, top))
329+
330+
331+
self.update(**kwargs)
332+
266333

267334
class GridSpecFromSubplotSpec(GridSpecBase):
268335
"""

lib/matplotlib/pyplot.py

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -923,6 +923,25 @@ def subplot_tool(targetfig=None):
923923
return ret
924924

925925

926+
927+
def tight_layout(pad=1.2, h_pad=None, w_pad=None):
928+
"""Adjust subplot parameters to give specified padding.
929+
930+
Parameters
931+
----------
932+
pad : float
933+
padding between the figure edge and the edges of subplots, as a fraction of the font-size.
934+
h_pad, w_pad : float
935+
padding (height/width) between edges of adjacent subplots.
936+
Defaults to `pad_inches`.
937+
"""
938+
939+
fig = gcf()
940+
fig.tight_layout(pad=pad, h_pad=h_pad, w_pad=w_pad)
941+
draw_if_interactive()
942+
943+
944+
926945
def box(on=None):
927946
"""
928947
Turn the axes box on or off according to *on*.

0 commit comments

Comments
 (0)