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

Skip to content

Commit 4cdd071

Browse files
authored
Merge pull request #12951 from anntzer/get_layout
MNT: Make Text._get_layout simpler to follow.
2 parents 5cdd2e5 + b140c65 commit 4cdd071

File tree

1 file changed

+55
-57
lines changed

1 file changed

+55
-57
lines changed

lib/matplotlib/text.py

Lines changed: 55 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -276,86 +276,87 @@ def _get_layout(self, renderer):
276276
if key in self._cached:
277277
return self._cached[key]
278278

279-
horizLayout = []
280-
281279
thisx, thisy = 0.0, 0.0
282-
xmin, ymin = 0.0, 0.0
283-
width, height = 0.0, 0.0
284-
lines = self.get_text().split('\n')
280+
lines = self.get_text().split("\n") # Ensures lines is not empty.
285281

286-
whs = np.zeros((len(lines), 2))
287-
horizLayout = np.zeros((len(lines), 4))
282+
ws = []
283+
hs = []
284+
xs = []
285+
ys = []
288286

289287
# Full vertical extent of font, including ascenders and descenders:
290-
tmp, lp_h, lp_bl = renderer.get_text_width_height_descent('lp',
291-
self._fontproperties,
292-
ismath=False)
293-
offsety = (lp_h - lp_bl) * self._linespacing
288+
_, lp_h, lp_d = renderer.get_text_width_height_descent(
289+
"lp", self._fontproperties, ismath=False)
290+
min_dy = (lp_h - lp_d) * self._linespacing
294291

295-
baseline = 0
296292
for i, line in enumerate(lines):
297293
clean_line, ismath = self.is_math_text(line, self.get_usetex())
298294
if clean_line:
299-
w, h, d = renderer.get_text_width_height_descent(clean_line,
300-
self._fontproperties,
301-
ismath=ismath)
295+
w, h, d = renderer.get_text_width_height_descent(
296+
clean_line, self._fontproperties, ismath=ismath)
302297
else:
303-
w, h, d = 0, 0, 0
298+
w = h = d = 0
304299

305-
# For multiline text, increase the line spacing when the
306-
# text net-height(excluding baseline) is larger than that
307-
# of a "l" (e.g., use of superscripts), which seems
308-
# what TeX does.
300+
# For multiline text, increase the line spacing when the text
301+
# net-height (excluding baseline) is larger than that of a "l"
302+
# (e.g., use of superscripts), which seems what TeX does.
309303
h = max(h, lp_h)
310-
d = max(d, lp_bl)
304+
d = max(d, lp_d)
311305

312-
whs[i] = w, h
306+
ws.append(w)
307+
hs.append(h)
313308

309+
# Metrics of the last line that are needed later:
314310
baseline = (h - d) - thisy
311+
315312
if i == 0:
316313
# position at baseline
317314
thisy = -(h - d)
318315
else:
319316
# put baseline a good distance from bottom of previous line
320-
thisy -= max(offsety, (h - d) * self._linespacing)
321-
horizLayout[i] = thisx, thisy, w, h
317+
thisy -= max(min_dy, (h - d) * self._linespacing)
318+
319+
xs.append(thisx) # == 0.
320+
ys.append(thisy)
321+
322322
thisy -= d
323-
width = max(width, w)
324-
descent = d
323+
324+
# Metrics of the last line that are needed later:
325+
descent = d
325326

326327
# Bounding box definition:
328+
width = max(ws)
329+
xmin = 0
330+
xmax = width
327331
ymax = 0
328-
# ymin is baseline of previous line minus the descent of this line
329-
ymin = horizLayout[-1][1] - descent
332+
ymin = ys[-1] - descent # baseline of last line minus its descent
330333
height = ymax - ymin
331-
xmax = xmin + width
332334

333335
# get the rotation matrix
334336
M = Affine2D().rotate_deg(self.get_rotation())
335337

336-
offsetLayout = np.zeros((len(lines), 2))
337-
offsetLayout[:] = horizLayout[:, 0:2]
338338
# now offset the individual text lines within the box
339-
if len(lines) > 1: # do the multiline aligment
340-
malign = self._get_multialignment()
341-
if malign == 'center':
342-
offsetLayout[:, 0] += width / 2.0 - horizLayout[:, 2] / 2.0
343-
elif malign == 'right':
344-
offsetLayout[:, 0] += width - horizLayout[:, 2]
339+
malign = self._get_multialignment()
340+
if malign == 'left':
341+
offset_layout = [(x, y) for x, y in zip(xs, ys)]
342+
elif malign == 'center':
343+
offset_layout = [(x + width / 2 - w / 2, y)
344+
for x, y, w in zip(xs, ys, ws)]
345+
elif malign == 'right':
346+
offset_layout = [(x + width - w, y)
347+
for x, y, w in zip(xs, ys, ws)]
345348

346349
# the corners of the unrotated bounding box
347-
cornersHoriz = np.array(
348-
[(xmin, ymin), (xmin, ymax), (xmax, ymax), (xmax, ymin)], float)
350+
corners_horiz = np.array(
351+
[(xmin, ymin), (xmin, ymax), (xmax, ymax), (xmax, ymin)])
349352

350353
# now rotate the bbox
351-
cornersRotated = M.transform(cornersHoriz)
352-
353-
txs = cornersRotated[:, 0]
354-
tys = cornersRotated[:, 1]
355-
354+
corners_rotated = M.transform(corners_horiz)
356355
# compute the bounds of the rotated box
357-
xmin, xmax = txs.min(), txs.max()
358-
ymin, ymax = tys.min(), tys.max()
356+
xmin = corners_rotated[:, 0].min()
357+
xmax = corners_rotated[:, 0].max()
358+
ymin = corners_rotated[:, 1].min()
359+
ymax = corners_rotated[:, 1].max()
359360
width = xmax - xmin
360361
height = ymax - ymin
361362

@@ -369,25 +370,25 @@ def _get_layout(self, renderer):
369370
# compute the text location in display coords and the offsets
370371
# necessary to align the bbox with that location
371372
if halign == 'center':
372-
offsetx = (xmin + width / 2.0)
373+
offsetx = (xmin + xmax) / 2
373374
elif halign == 'right':
374-
offsetx = (xmin + width)
375+
offsetx = xmax
375376
else:
376377
offsetx = xmin
377378

378379
if valign == 'center':
379-
offsety = (ymin + height / 2.0)
380+
offsety = (ymin + ymax) / 2
380381
elif valign == 'top':
381-
offsety = (ymin + height)
382+
offsety = ymax
382383
elif valign == 'baseline':
383384
offsety = ymin + descent
384385
elif valign == 'center_baseline':
385386
offsety = ymin + height - baseline / 2.0
386387
else:
387388
offsety = ymin
388389
else:
389-
xmin1, ymin1 = cornersHoriz[0]
390-
xmax1, ymax1 = cornersHoriz[2]
390+
xmin1, ymin1 = corners_horiz[0]
391+
xmax1, ymax1 = corners_horiz[2]
391392

392393
if halign == 'center':
393394
offsetx = (xmin1 + xmax1) / 2.0
@@ -415,12 +416,9 @@ def _get_layout(self, renderer):
415416
bbox = Bbox.from_bounds(xmin, ymin, width, height)
416417

417418
# now rotate the positions around the first x,y position
418-
xys = M.transform(offsetLayout)
419-
xys -= (offsetx, offsety)
420-
421-
xs, ys = xys[:, 0], xys[:, 1]
419+
xys = M.transform(offset_layout) - (offsetx, offsety)
422420

423-
ret = bbox, list(zip(lines, whs, xs, ys)), descent
421+
ret = bbox, list(zip(lines, zip(ws, hs), *xys.T)), descent
424422
self._cached[key] = ret
425423
return ret
426424

0 commit comments

Comments
 (0)