Mario
Mario

Reputation: 1966

Problem with symbol opacity of errorbar within legend

I'm trying to indicate perfectly symbols within legend once I want to plot complicated combinations of line and errorbar in grid plots. I noticed that it's not easy to apply desired opacity for any symbol kinds when they are error bar.

I have tried following checking this post unsuccessfully.

import matplotlib.pyplot as plt
from matplotlib.collections import PathCollection
from matplotlib.legend_handler import HandlerPathCollection, HandlerLine2D, HandlerErrorbar


x1 = np.linspace(0,1,8)
y1 = np.random.rand(8)

# Compute prediction intervals
sum_of_squares_mid = np.sum((x1 - y1) ** 2)
std_mid            = np.sqrt(1 / (len(x1) - 2) * sum_of_squares_mid)

# Plot the prediction intervals
y_err_mid = np.vstack([std_mid, std_mid]) * 1.96

plt.plot(x1, y1, 'bo', label='label', marker=r"$\clubsuit$",  alpha=0.2)                                                 # Default alpha is 1.0.
plt.errorbar(x1, y1, yerr=y_err_mid, fmt="o", ecolor="#FF0009", capsize=3, color="#FF0009", label="Errorbar", alpha=.1)  # Default alpha is 1.0.


def update(handle, orig):
    handle.update_from(orig)
    handle.set_alpha(1)

plt.legend(handler_map={PathCollection : HandlerPathCollection(update_func = update),
                            plt.Line2D : HandlerLine2D(        update_func = update),
                          plt.errorbar : HandlerErrorbar(      update_func = update) # I added this but it deos not apply alpha=1 only for errobar symbol in legend
                        })

plt.show()

My current output:

resulting plot without updated alpha

Upvotes: 0

Views: 43

Answers (1)

Luca
Luca

Reputation: 654

It appears that you were not specifying the right handler for the second Artist which is an ErrorbarContainer, thus the set_alpha(1) instruction was not executed for that object.

Indeed, importing

import matplotlib.pyplot as plt
from matplotlib.container import ErrorbarContainer
from matplotlib.legend_handler import HandlerLine2D, HandlerErrorbar

and then modifying the handler_map to

def update(handle, orig):
    handle.update_from(orig)
    handle.set_alpha(1)

leg = plt.legend(handler_map={
    plt.Line2D : HandlerLine2D(update_func = update),
    ErrorbarContainer: HandlerErrorbar(update_func = update)
                        })

results in

Figure with solid symbols in legend

Hope this helps!

Upvotes: 1

Related Questions