Python matplotlib: Change axis labels/legend from bold to regular weight

2024/10/1 17:31:15

I'm trying to make some publication-quality plots, but I have encountered a small problem. It seems by default that matplotlib axis labels and legend entries are weighted heavier than the axis tick marks. Is there anyway to force the axis labels/legend entries to be the same weight as the tick marks?

import matplotlib.pyplot as plt
import numpy as npplt.rc('text',usetex=True)
font = {'family':'serif','size':16}
plt.rc('font',**font)
plt.rc('legend',**{'fontsize':14})x = np.linspace(0,2*np.pi,100)
y = np.sin(x)fig = plt.figure(figsize=(5,5))
p1, = plt.plot(x,y)
p2, = plt.plot(x,x**2)
plt.xlabel('x-Axis')
plt.ylabel('y-Axis')
plt.legend([p1,p2],['Sin(x)','x$^2$'])
plt.gcf().subplots_adjust(left=0.2)
plt.gcf().subplots_adjust(bottom=0.15)
plt.savefig('Test.eps',bbox_inches='tight',format='eps')
plt.show()

I can use math-mode, but the problem (annoyance) is when I have a sentence for a label, i.e.,

plt.xlabel('$\mathrm{This is the x-axis}$') 

which squishes it all together. I can fix it by using

plt.xlabel('$\mathrm{This\: is\: the\: x-axis}$')

but that needs a lot of punctuation. I was hoping there was something that I could change that would allow me to bypass the \mathrm{} format, and use standard TeX format.

The other option I tried, was using \text instead of \mathrm, but it seems that Python's interpreter doesn't recognize this without loading the package amsmath. I have also tried:

import matplotlib
import matplotlib.pyplot as plt
import numpy as npplt.rc('text',usetex=True)
font = {'family':'serif','size':16}
plt.rc('font',**font)
plt.rc('legend',**{'fontsize':14})
matplotlib.rcParams['text.latex.preamble']=[r'\usepackage{amsmath}']x = np.linspace(0,2*np.pi,100)
y = np.sin(x)fig = plt.figure(figsize=(5,5))
p1, = plt.plot(x,y)
p2, = plt.plot(x,x**2)
plt.xlabel(r'$\text{this is the x-Axis}$')
plt.ylabel('$y-Axis$')
plt.legend([p1,p2],['Sin(x)','x$^2$'])
plt.gcf().subplots_adjust(left=0.2)
plt.gcf().subplots_adjust(bottom=0.15)
plt.savefig('Test.eps',bbox_inches='tight',format='eps')
plt.show()

This doesn't return the desired result either.

Answer

The other answer provides a work-around to the problem... However, the problem is very specific to matplotlib and the implementation of the LateX backend.

First of all, the rc parameter controlling the font weight of the axis labels is 'axes.labelweight', which by default is set to u'normal'. This means that the labels should already be in regular weight.

The reason why the font appears to be bold can be found in matplotlib/texmanager.py:

  1. The font family is chosen by 'font.family', in the case of the OP, this is serif.

  2. Then, the array 'font.<font.family>' (here: font.serif) is evaluated, and the declaration of all fonts is added to the LateX preamble. Among those declarations is the line

    \renewcommand{\rmdefault}{pnc}
    

    which sets the default to New Century School Book which appears to be a bold version of Computer Modern Roman.

In conclusion, the shortest way to solve the problem is to set font.serif to contain only Computer Modern Roman:

font = {'family':'serif','size':16, 'serif': ['computer modern roman']}

This has the additional benefit that it works for all elements, even for labels and other captions - without dirty tricks using the math mode: enter image description here


Here is the complete code to generate the plot:

import matplotlib
import matplotlib.pyplot as plt
import numpy as npplt.rc('text',usetex=True)
#font = {'family':'serif','size':16}
font = {'family':'serif','size':16, 'serif': ['computer modern roman']}
plt.rc('font',**font)
plt.rc('legend',**{'fontsize':14})
matplotlib.rcParams['text.latex.preamble']=[r'\usepackage{amsmath}']x = np.linspace(0,2*np.pi,100)
y = np.sin(x)fig = plt.figure(figsize=(5,5))
p1, = plt.plot(x,y)
p2, = plt.plot(x,x**2)
plt.xlabel(r'$\text{this is the x-Axis}$')
plt.ylabel('$y-Axis$')
plt.legend([p1,p2],['Sin(x)','x$^2$'])
plt.gcf().subplots_adjust(left=0.2)
plt.gcf().subplots_adjust(bottom=0.15)
plt.savefig('Test.eps',bbox_inches='tight',format='eps')
plt.show()
https://en.xdnf.cn/q/70944.html

Related Q&A

Negative extra_requires in Python setup.py

Id like to make a Python package that installs a dependency by default unless the user specially signals they do not want that.Example:pip install package[no-django]Does current pip and setup.py mechan…

Get Type in Robot Framework

Could you tell me about how to get the variable type in Robot Framework.${ABC} Set Variable Test ${XYZ} Set Variable 1233Remark: Get the variable Type such as string, intget ${ABC} type = strin…

Keras 2, TypeError: cant pickle _thread.lock objects

I am using Keras to create an ANN and do a grid search on the network. I have encountered the following error while running the code below:model = KerasClassifier(build_fn=create_model(input_dim), verb…

How to remove minimize/maximize buttons while preserving the icon?

Is it possible to display the icon for my toplevel and root window after removing the minimize and maximize buttons? I tried using -toolwindow but the icon cant be displayed afterwards. Is there anoth…

Undefined reference to `PyString_FromString

I have this C code:... [SNIP] ... for(Node = Plugin.Head; Node != NULL; Node = Node->Next) {//Create new python sub-interpreterNode->Interpreter = Py_NewInterpreter();if(Node->Interpreter == N…

How to call a method from a different blueprint in Flask?

I have an application with multiple blueprinted modules.I would like to call a method (a route) that would normally return a view or render a template, from within a different blueprints route.How can …

Dynamically define functions with varying signature

What I want to accomplish:dct = {foo:0, bar:1, baz:2} def func(**dct):pass #function signature is now func(foo=0, bar=1, baz=2)However, the ** syntax is obviously clashing here between expanding a dict…

python pandas plot with uneven timeseries index (with count evenly distributed)

My dataframe has uneven time index.how could I find a way to plot the data, and local the index automatically? I searched here, and I know I can plot something like e.plot()but the time index (x axis)…

python OpenAI gym monitor creates json files in the recording directory

I am implementing value iteration on the gym CartPole-v0 environment and would like to record the video of the agents actions in a video file. I have been trying to implement this using the Monitor wra…

Install xgboost under python with 32-bit msys failing

Trying to install xgboost is failing..? The version is Anaconda 2.1.0 (64-bit) on Windows & enterprise. How do I proceed? I have been using R it seems its quite easy to install new package in R …