The following MWE
import matplotlib
matplotlib.use('TkAgg')
import matplotlib.pyplot as plt
# Use latex
import os
os.environ["PATH"] += os.pathsep + '/usr/local/texlive/2024/bin/x86_64-linux'
if __name__ == '__main__':
plt.rcParams.update({
"text.usetex": True,
"font.family": "serif",
"font.serif": "Computer Modern Roman",
})
test_data = 10
test_data_2 = 24
# Create plot and axis
fig, ax = plt.subplots()
# Plot
ax.plot([i for i in range(test_data)], [i for i in range(test_data)], label="Test")
ax.tick_params(bottom=False)
# Define x axis
x_axis = ['30', '40', '50'] * (test_data_2 // 3)
ax.set_xticks(range(len(x_axis)), labels=(x_axis))
# Add second x axis
sec2 = ax.secondary_xaxis(location=0)
sec2.set_xticks([5.5 + 12 * i for i in range(test_data_2 // 12)],
labels=[f'\n\n{5 + i * 5}' for i in range(test_data_2 // 12)])
sec2.tick_params('x', length=0)
plt.show()
I would now like to be able to precisely move the secondary x axis up a bit (instead of using inprecise '\n'). How would this be possible or should I maybe use a whole different approach for getting a secondary x axis?
Edit: As asked in the comments: The purpose of the secondary axis actually just for being able to add multiple layers of xticklabels.
You can position the second Axes using the location
argument to the secondary_xaxis
function.
location
{'top', 'bottom', 'left', 'right'}
orfloat
The position to put the secondary axis. Strings can be 'top' or 'bottom' for orientation='x' and 'right' or 'left' for orientation='y'. A float indicates the relative position on the parent Axes to put the new Axes, 0.0 being the bottom (or left) and 1.0 being the top (or right).
To move this below the primary x-axis, we can therefore use a small negative number.
For example:
sec2 = ax.secondary_xaxis(location=-0.07)
sec2.set_xticks([5.5 + 12 * i for i in range(test_data_2 // 12)],
labels=[f'{5 + i * 5}' for i in range(test_data_2 // 12)])
sec2.tick_params('x', length=0)
yields:
To remove the horizontal line, we can set the visibility of the bottom spine of the Axes to False:
sec2 = ax.secondary_xaxis(location=-0.07)
sec2.set_xticks([5.5 + 12 * i for i in range(test_data_2 // 12)],
labels=[f'{5 + i * 5}' for i in range(test_data_2 // 12)])
sec2.tick_params('x', length=0)
sec2.spines['bottom'].set_visible(False)