From 962516d3cf6889b9b0e17578bfe7f8a93213bb22 Mon Sep 17 00:00:00 2001 From: Sanchit Rishi Date: Sun, 8 Feb 2026 21:54:26 +0530 Subject: [PATCH 1/8] MNT: Normalize internal set_foreground calls to RGBA (#31105) --- lib/matplotlib/collections.py | 2 +- lib/matplotlib/patheffects.py | 4 ++-- lib/matplotlib/text.py | 4 ++-- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/lib/matplotlib/collections.py b/lib/matplotlib/collections.py index 23f516aa6337..266972c27625 100644 --- a/lib/matplotlib/collections.py +++ b/lib/matplotlib/collections.py @@ -411,7 +411,7 @@ def draw(self, renderer): gc.set_capstyle(self._capstyle) if do_single_path_optimization: - gc.set_foreground(tuple(edgecolors[0])) + gc.set_foreground(mcolors.to_rgba(edgecolors[0]), isRGBA=True) gc.set_linewidth(self._linewidths[0]) gc.set_dashes(*self._linestyles[0]) gc.set_antialiased(self._antialiaseds[0]) diff --git a/lib/matplotlib/patheffects.py b/lib/matplotlib/patheffects.py index f700feac6292..ae808eb62fbe 100644 --- a/lib/matplotlib/patheffects.py +++ b/lib/matplotlib/patheffects.py @@ -269,7 +269,7 @@ def draw_path(self, renderer, gc, tpath, affine, rgbFace): else: shadow_rgbFace = self._shadow_rgbFace - gc0.set_foreground("none") + gc0.set_foreground(mcolors.to_rgba("none"), isRGBA=True) gc0.set_alpha(self._alpha) gc0.set_linewidth(0) @@ -331,7 +331,7 @@ def draw_path(self, renderer, gc, tpath, affine, rgbFace): else: shadow_rgbFace = self._shadow_color - gc0.set_foreground(shadow_rgbFace) + gc0.set_foreground(mcolors.to_rgba(shadow_rgbFace), isRGBA=True) gc0.set_alpha(self._alpha) gc0 = self._update_gc(gc0, self._gc) diff --git a/lib/matplotlib/text.py b/lib/matplotlib/text.py index d794cab1339b..cbeba1f84307 100644 --- a/lib/matplotlib/text.py +++ b/lib/matplotlib/text.py @@ -11,7 +11,7 @@ import numpy as np import matplotlib as mpl -from . import _api, artist, cbook, _docstring +from . import _api, artist, cbook, _docstring, colors as mcolors from .artist import Artist from .font_manager import FontProperties from .patches import FancyArrowPatch, FancyBboxPatch, Rectangle @@ -864,7 +864,7 @@ def draw(self, renderer): self._bbox_patch.draw(renderer) gc = renderer.new_gc() - gc.set_foreground(self.get_color()) + gc.set_foreground(mcolors.to_rgba(self.get_color()), isRGBA=True) gc.set_alpha(self.get_alpha()) gc.set_url(self._url) gc.set_antialiased(self._antialiased) From 942810d513258163cba99bad70c74f6bccf7b15e Mon Sep 17 00:00:00 2001 From: Sanchit Rishi Date: Mon, 9 Feb 2026 15:53:05 +0530 Subject: [PATCH 2/8] Update lib/matplotlib/collections.py Co-authored-by: Tim Hoffmann <2836374+timhoffm@users.noreply.github.com> --- lib/matplotlib/collections.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/matplotlib/collections.py b/lib/matplotlib/collections.py index 266972c27625..92e176d7051f 100644 --- a/lib/matplotlib/collections.py +++ b/lib/matplotlib/collections.py @@ -411,7 +411,7 @@ def draw(self, renderer): gc.set_capstyle(self._capstyle) if do_single_path_optimization: - gc.set_foreground(mcolors.to_rgba(edgecolors[0]), isRGBA=True) + gc.set_foreground(tuple(edgecolors[0]), isRGBA=True) gc.set_linewidth(self._linewidths[0]) gc.set_dashes(*self._linestyles[0]) gc.set_antialiased(self._antialiaseds[0]) From 6e808cd904491514b993483efb1cf48ac8464f5d Mon Sep 17 00:00:00 2001 From: Sanchit Rishi Date: Mon, 9 Feb 2026 19:50:17 +0530 Subject: [PATCH 3/8] DEBUG: Force file update --- lib/matplotlib/collections.py | 1 + 1 file changed, 1 insertion(+) diff --git a/lib/matplotlib/collections.py b/lib/matplotlib/collections.py index 92e176d7051f..87a046db17a2 100644 --- a/lib/matplotlib/collections.py +++ b/lib/matplotlib/collections.py @@ -2684,3 +2684,4 @@ def set_array(self, A): # the set of Polys that we are drawing if not np.array_equal(prev_unmask, self._get_unmasked_polys()): self._set_unmasked_verts() +# Force update From 3a34296cfe0587d6a9725b076d7458101e57df08 Mon Sep 17 00:00:00 2001 From: Sanchit Rishi Date: Mon, 9 Feb 2026 19:50:30 +0530 Subject: [PATCH 4/8] FIX: Revert debug comment and ensure correct indentation --- lib/matplotlib/collections.py | 1 - 1 file changed, 1 deletion(-) diff --git a/lib/matplotlib/collections.py b/lib/matplotlib/collections.py index 87a046db17a2..92e176d7051f 100644 --- a/lib/matplotlib/collections.py +++ b/lib/matplotlib/collections.py @@ -2684,4 +2684,3 @@ def set_array(self, A): # the set of Polys that we are drawing if not np.array_equal(prev_unmask, self._get_unmasked_polys()): self._set_unmasked_verts() -# Force update From 2797ff062579c0497391fc2d8b8c7045a0c9e49d Mon Sep 17 00:00:00 2001 From: Sanchit Rishi Date: Mon, 9 Feb 2026 19:55:32 +0530 Subject: [PATCH 5/8] FIX: Programmatically fix indentation --- lib/matplotlib/collections.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/matplotlib/collections.py b/lib/matplotlib/collections.py index 92e176d7051f..bbc8e57d7a05 100644 --- a/lib/matplotlib/collections.py +++ b/lib/matplotlib/collections.py @@ -411,7 +411,7 @@ def draw(self, renderer): gc.set_capstyle(self._capstyle) if do_single_path_optimization: - gc.set_foreground(tuple(edgecolors[0]), isRGBA=True) + gc.set_foreground(tuple(edgecolors[0]), isRGBA=True) gc.set_linewidth(self._linewidths[0]) gc.set_dashes(*self._linestyles[0]) gc.set_antialiased(self._antialiaseds[0]) From 72aa0415961bf7944cb0b662301934e9e143c4e3 Mon Sep 17 00:00:00 2001 From: Sanchit Rishi Date: Tue, 10 Feb 2026 19:38:00 +0530 Subject: [PATCH 6/8] MNT: Apply review suggestions from rcomer --- lib/matplotlib/backend_bases.py | 15 +++++++++++++-- lib/mpl_toolkits/axisartist/axis_artist.py | 3 ++- 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/lib/matplotlib/backend_bases.py b/lib/matplotlib/backend_bases.py index 7f6c01089d0d..e2073e7dbd83 100644 --- a/lib/matplotlib/backend_bases.py +++ b/lib/matplotlib/backend_bases.py @@ -411,10 +411,21 @@ def cycle_or_default(seq, default=None): gc0.set_linewidth(lw) if Nlinestyles: gc0.set_dashes(*ls) - if len(ec) == 4 and ec[3] == 0.0: + ec_is_seq = ( + isinstance(ec, (np.ndarray, list, tuple)) + and not isinstance(ec, str) + ) + if isinstance(ec, np.ndarray): + ec = tuple(ec.tolist()) + elif isinstance(ec, list): + ec = tuple(ec) + if ec_is_seq and len(ec) == 4 and ec[3] == 0.0: gc0.set_linewidth(0) else: - gc0.set_foreground(ec) + if ec_is_seq and len(ec) == 4: + gc0.set_foreground(ec, isRGBA=True) + else: + gc0.set_foreground(ec) if Nhatchcolors: gc0.set_hatch_color(hc) if fc is not None and len(fc) == 4 and fc[3] == 0: diff --git a/lib/mpl_toolkits/axisartist/axis_artist.py b/lib/mpl_toolkits/axisartist/axis_artist.py index e4628f99e420..dd0ed6b583f7 100644 --- a/lib/mpl_toolkits/axisartist/axis_artist.py +++ b/lib/mpl_toolkits/axisartist/axis_artist.py @@ -178,7 +178,8 @@ def draw(self, renderer): return gc = renderer.new_gc() - gc.set_foreground(self.get_markeredgecolor()) + edgecolor = mcolors.to_rgba(self.get_markeredgecolor()) + gc.set_foreground(edgecolor, isRGBA=True) gc.set_linewidth(self.get_markeredgewidth()) gc.set_alpha(self._alpha) From 9c29a9b3dd03567b152cd425fb9aad48e64e717a Mon Sep 17 00:00:00 2001 From: Sanchit Rishi Date: Mon, 16 Feb 2026 21:01:20 +0530 Subject: [PATCH 7/8] MNT: Simplify edgecolor handling in _iter_collection --- lib/matplotlib/backend_bases.py | 26 +++++++++++++++----------- 1 file changed, 15 insertions(+), 11 deletions(-) diff --git a/lib/matplotlib/backend_bases.py b/lib/matplotlib/backend_bases.py index e2073e7dbd83..5af7987acd3d 100644 --- a/lib/matplotlib/backend_bases.py +++ b/lib/matplotlib/backend_bases.py @@ -411,21 +411,25 @@ def cycle_or_default(seq, default=None): gc0.set_linewidth(lw) if Nlinestyles: gc0.set_dashes(*ls) - ec_is_seq = ( - isinstance(ec, (np.ndarray, list, tuple)) - and not isinstance(ec, str) - ) + # In the common case (Collections), edgecolors are already + # normalized to RGBA float sequences (typically Nx4 arrays). if isinstance(ec, np.ndarray): - ec = tuple(ec.tolist()) + ec_rgba = tuple(ec.tolist()) elif isinstance(ec, list): - ec = tuple(ec) - if ec_is_seq and len(ec) == 4 and ec[3] == 0.0: - gc0.set_linewidth(0) + ec_rgba = tuple(ec) + elif isinstance(ec, tuple): + ec_rgba = ec else: - if ec_is_seq and len(ec) == 4: - gc0.set_foreground(ec, isRGBA=True) + ec_rgba = None + + if ec_rgba is not None and len(ec_rgba) == 4: + # Fully transparent edges are treated as "no stroke". + if ec_rgba[3] == 0.0: + gc0.set_linewidth(0) else: - gc0.set_foreground(ec) + gc0.set_foreground(ec_rgba, isRGBA=True) + else: + gc0.set_foreground(ec) if Nhatchcolors: gc0.set_hatch_color(hc) if fc is not None and len(fc) == 4 and fc[3] == 0: From bd51b341cc1eb3c8c8bd1b1e505b88095b54fa6e Mon Sep 17 00:00:00 2001 From: Sanchit Rishi Date: Tue, 17 Feb 2026 21:39:27 +0530 Subject: [PATCH 8/8] MNT: Normalize edgecolor via to_rgba in _iter_collection --- lib/matplotlib/backend_bases.py | 23 +++++------------------ 1 file changed, 5 insertions(+), 18 deletions(-) diff --git a/lib/matplotlib/backend_bases.py b/lib/matplotlib/backend_bases.py index 5af7987acd3d..fc19f6108d13 100644 --- a/lib/matplotlib/backend_bases.py +++ b/lib/matplotlib/backend_bases.py @@ -411,25 +411,12 @@ def cycle_or_default(seq, default=None): gc0.set_linewidth(lw) if Nlinestyles: gc0.set_dashes(*ls) - # In the common case (Collections), edgecolors are already - # normalized to RGBA float sequences (typically Nx4 arrays). - if isinstance(ec, np.ndarray): - ec_rgba = tuple(ec.tolist()) - elif isinstance(ec, list): - ec_rgba = tuple(ec) - elif isinstance(ec, tuple): - ec_rgba = ec + ec_rgba = colors.to_rgba(ec) + # Fully transparent edges are treated as "no stroke". + if ec_rgba[3] == 0.0: + gc0.set_linewidth(0) else: - ec_rgba = None - - if ec_rgba is not None and len(ec_rgba) == 4: - # Fully transparent edges are treated as "no stroke". - if ec_rgba[3] == 0.0: - gc0.set_linewidth(0) - else: - gc0.set_foreground(ec_rgba, isRGBA=True) - else: - gc0.set_foreground(ec) + gc0.set_foreground(ec_rgba, isRGBA=True) if Nhatchcolors: gc0.set_hatch_color(hc) if fc is not None and len(fc) == 4 and fc[3] == 0: