Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit dc81103

Browse filesBrowse files
tacaswellmeeseeksmachine
authored andcommitted
Backport PR #16770: Fix tuple markers
1 parent 15b1cb5 commit dc81103
Copy full SHA for dc81103

File tree

Expand file treeCollapse file tree

2 files changed

+108
-0
lines changed
Filter options
Expand file treeCollapse file tree

2 files changed

+108
-0
lines changed

‎lib/matplotlib/markers.py

Copy file name to clipboardExpand all lines: lib/matplotlib/markers.py
+1Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -347,6 +347,7 @@ def _set_tuple_marker(self):
347347
self._joinstyle = 'bevel'
348348
else:
349349
raise ValueError(f"Unexpected tuple marker: {marker}")
350+
self._transform = Affine2D().scale(0.5).rotate_deg(rotation)
350351

351352
def _set_mathtext_path(self):
352353
"""

‎lib/matplotlib/tests/test_marker.py

Copy file name to clipboardExpand all lines: lib/matplotlib/tests/test_marker.py
+107Lines changed: 107 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
import numpy as np
2+
import matplotlib.pyplot as plt
23
from matplotlib import markers
34
from matplotlib.path import Path
5+
from matplotlib.testing.decorators import check_figures_equal
46

57
import pytest
68

@@ -26,3 +28,108 @@ def test_marker_path():
2628
path = Path([[0, 0], [1, 0]], [Path.MOVETO, Path.LINETO])
2729
# Checking this doesn't fail.
2830
marker_style.set_marker(path)
31+
32+
33+
class UnsnappedMarkerStyle(markers.MarkerStyle):
34+
"""
35+
A MarkerStyle where the snap threshold is force-disabled.
36+
37+
This is used to compare to polygon/star/asterisk markers which do not have
38+
any snap threshold set.
39+
"""
40+
def _recache(self):
41+
super()._recache()
42+
self._snap_threshold = None
43+
44+
45+
@check_figures_equal()
46+
def test_poly_marker(fig_test, fig_ref):
47+
ax_test = fig_test.add_subplot()
48+
ax_ref = fig_ref.add_subplot()
49+
50+
# Note, some reference sizes must be different because they have unit
51+
# *length*, while polygon markers are inscribed in a circle of unit
52+
# *radius*. This introduces a factor of np.sqrt(2), but since size is
53+
# squared, that becomes 2.
54+
size = 20**2
55+
56+
# Squares
57+
ax_test.scatter([0], [0], marker=(4, 0, 45), s=size)
58+
ax_ref.scatter([0], [0], marker='s', s=size/2)
59+
60+
# Diamonds, with and without rotation argument
61+
ax_test.scatter([1], [1], marker=(4, 0), s=size)
62+
ax_ref.scatter([1], [1], marker=UnsnappedMarkerStyle('D'), s=size/2)
63+
ax_test.scatter([1], [1.5], marker=(4, 0, 0), s=size)
64+
ax_ref.scatter([1], [1.5], marker=UnsnappedMarkerStyle('D'), s=size/2)
65+
66+
# Pentagon, with and without rotation argument
67+
ax_test.scatter([2], [2], marker=(5, 0), s=size)
68+
ax_ref.scatter([2], [2], marker=UnsnappedMarkerStyle('p'), s=size)
69+
ax_test.scatter([2], [2.5], marker=(5, 0, 0), s=size)
70+
ax_ref.scatter([2], [2.5], marker=UnsnappedMarkerStyle('p'), s=size)
71+
72+
# Hexagon, with and without rotation argument
73+
ax_test.scatter([3], [3], marker=(6, 0), s=size)
74+
ax_ref.scatter([3], [3], marker='h', s=size)
75+
ax_test.scatter([3], [3.5], marker=(6, 0, 0), s=size)
76+
ax_ref.scatter([3], [3.5], marker='h', s=size)
77+
78+
# Rotated hexagon
79+
ax_test.scatter([4], [4], marker=(6, 0, 30), s=size)
80+
ax_ref.scatter([4], [4], marker='H', s=size)
81+
82+
# Octagons
83+
ax_test.scatter([5], [5], marker=(8, 0, 22.5), s=size)
84+
ax_ref.scatter([5], [5], marker=UnsnappedMarkerStyle('8'), s=size)
85+
86+
ax_test.set(xlim=(-0.5, 5.5), ylim=(-0.5, 5.5))
87+
ax_ref.set(xlim=(-0.5, 5.5), ylim=(-0.5, 5.5))
88+
89+
90+
def test_star_marker():
91+
# We don't really have a strict equivalent to this marker, so we'll just do
92+
# a smoke test.
93+
size = 20**2
94+
95+
fig, ax = plt.subplots()
96+
ax.scatter([0], [0], marker=(5, 1), s=size)
97+
ax.scatter([1], [1], marker=(5, 1, 0), s=size)
98+
ax.set(xlim=(-0.5, 0.5), ylim=(-0.5, 1.5))
99+
100+
101+
# The asterisk marker is really a star with 0-size inner circle, so the ends
102+
# are corners and get a slight bevel. The reference markers are just singular
103+
# lines without corners, so they have no bevel, and we need to add a slight
104+
# tolerance.
105+
@check_figures_equal(tol=1.45)
106+
def test_asterisk_marker(fig_test, fig_ref, request):
107+
ax_test = fig_test.add_subplot()
108+
ax_ref = fig_ref.add_subplot()
109+
110+
# Note, some reference sizes must be different because they have unit
111+
# *length*, while asterisk markers are inscribed in a circle of unit
112+
# *radius*. This introduces a factor of np.sqrt(2), but since size is
113+
# squared, that becomes 2.
114+
size = 20**2
115+
116+
def draw_ref_marker(y, style, size):
117+
# As noted above, every line is doubled. Due to antialiasing, these
118+
# doubled lines make a slight difference in the .png results.
119+
ax_ref.scatter([y], [y], marker=UnsnappedMarkerStyle(style), s=size)
120+
if request.getfixturevalue('ext') == 'png':
121+
ax_ref.scatter([y], [y], marker=UnsnappedMarkerStyle(style),
122+
s=size)
123+
124+
# Plus
125+
ax_test.scatter([0], [0], marker=(4, 2), s=size)
126+
draw_ref_marker(0, '+', size)
127+
ax_test.scatter([0.5], [0.5], marker=(4, 2, 0), s=size)
128+
draw_ref_marker(0.5, '+', size)
129+
130+
# Cross
131+
ax_test.scatter([1], [1], marker=(4, 2, 45), s=size)
132+
draw_ref_marker(1, 'x', size/2)
133+
134+
ax_test.set(xlim=(-0.5, 1.5), ylim=(-0.5, 1.5))
135+
ax_ref.set(xlim=(-0.5, 1.5), ylim=(-0.5, 1.5))

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.