如何美化 Matplotlib 的工具欄和繪圖風格


前言

matplotlib 功能十分強大,就是工具欄丑了點。忍了一個學期之后,還是決定自己動手,魔改一波 matplotlib 的工具欄樣式。同時給大家分享一下自己按照 MATLAB 寫的 matplotlib 樣式文件。注意:代碼中 matplotlib 版本為 3.3.4,其他版本效果會不一樣

工具欄的美化

matplotlib 工具欄有三種模式:Nonetoolbar2toolmanager,默認 toolbar2, 我們可以通過 plt.rcParams['toolbar'] 來更換模式。在 None 模式下,圖窗中不存在工具欄;toolbar2toolmanager 長得很像,就是后者多了一個幫助按鈕。先來看一下 matplotlib 工具欄本來的樣子(后端使用的是Qt5Agg):

可以看到又黑又粗的圖標搭配上灰色的背景,效果十分感人。上面也已經提到了,工具欄有三種模式,拋開 None 不看,如果我們想要修改工具欄的樣式,就需要分別修改 toolbar2toolmanager 這兩種模式下的樣式。從 matplotlib.backends.backend_qt5 的第600行開始有:

def _get_toolbar(self, canvas, parent):
    # must be inited after the window, drawingArea and figure
    # attrs are set
    if matplotlib.rcParams['toolbar'] == 'toolbar2':
        toolbar = NavigationToolbar2QT(canvas, parent, True)
    elif matplotlib.rcParams['toolbar'] == 'toolmanager':
        toolbar = ToolbarQt(self.toolmanager, self.window)
    else:
        toolbar = None
    return toolbar

從源碼中可以得知兩種模式下的工具欄分別是 NavigationToolbar2QTToolbarQt 的實例。既然是用 QT 寫的,那要美化工具欄豈不是易如反掌?代碼擼起來 []( ̄▽ ̄)*。分別在 NavigationToolbar2QTToolbarQt 的構造函數的最后一行加上:

self.setStyleSheet("""QToolBar{background:white}
                      QLabel{font:11pt 'Consolas'}""")

QToolBar{background:white} 設置工具欄的背景色為白色,QLabel{font:11pt 'Consolas'} 設置的工具欄的字體為 11pt 的 Consolas 。修改完層疊樣式之后,我們來換一波圖標,圖標、字體以及mplstyle文件放在了百度網盤(提取碼:nlnv),用這些圖標替換掉 Lib\site-packages\matplotlib\mpl-data\images 中的自帶圖標,工具欄的美化就大功告成了( ̄︶ ̄)↗ 。

繪圖樣式的美化

matplotlib 可以自定義繪圖風格,這是它強大之處的體現。打開C盤用戶文件夾的.matplotlib\stylelib,我們可以看到一些 .mplstyle 文件,這些文件就是某種繪圖風格的具體配置。我們在這個目錄下創建一個matlab.mplstye 文件,往里面寫入:

## ***************************************************************************
## * AXES                                                                    *
## ***************************************************************************
axes.grid :       True
axes.axisbelow :  True
axes.facecolor :  white
axes.prop_cycle : cycler('color', ['0072BD', 'D95319', 'EDB120', '7E2F8E', '77AC30', '4DBEEE', 'A2142F'])



## ***************************************************************************
## * FIGURE                                                                  *
## ***************************************************************************
figure.dpi :        140
figure.figsize :    8, 6




## ***************************************************************************
## * TICKS                                                                   *
## ***************************************************************************
xtick.direction :       in
xtick.major.size :      6
xtick.major.width :     0.5
xtick.minor.size :      1.5
xtick.minor.width :     0.5
# xtick.minor.visible :   True
xtick.top : True

ytick.direction :       in
ytick.major.size :      6
ytick.major.width :     0.5
ytick.minor.size :      1.5
ytick.minor.width :     0.5
# ytick.minor.visible :   True
ytick.right :           True



## ***************************************************************************
## * LINES                                                                   *
## ***************************************************************************
axes.linewidth :  0.5
lines.linewidth : 1



## ***************************************************************************
## * SAVING FIGURES                                                          *
## ***************************************************************************
savefig.dpi : 	     300
savefig.bbox :       tight
savefig.pad_inches : 0.05



## ***************************************************************************
## * FONT                                                                    *
## ***************************************************************************
font.size :        11
font.family :      serif
font.serif :       Latin Modern Roman, Times New Roman
font.sans-serif :  Helvetica
mathtext.default:  it
mathtext.fallback: cm
mathtext.fontset : cm



## ***************************************************************************
## * GRIDS                                                                   *
## ***************************************************************************
grid.color :     0.8
grid.alpha :     0.64
grid.linewidth : 0.5
grid.linestyle : -



## ***************************************************************************
## * LEGEND                                                                  *
## ***************************************************************************
legend.loc:         best
legend.shadow :     False
legend.frameon :    True
legend.fancybox :   False
legend.numpoints :  1
legend.edgecolor:   0
legend.framealpha : 1

在繪圖之前,調用一下 plt.style.use('matlab'),就可以將默認繪圖風格換成上面定義的風格。

測試

import numpy as np
import matplotlib.pyplot as plt


x = np.arange(0, 2 * np.pi, 0.01)
y = np.sin(x)
z = 0.5 * np.sin(x)

# 更換工具欄模式
# plt.rcParams['toolbar'] = 'toolmanager'
# 設置繪圖樣式
plt.style.use('matlab')

fig = plt.figure(num='sine wave')  #type:plt.Figure
plt.plot(x, y, x, z)
plt.axis((0, 2 * np.pi, -1, 1))

plt.xlabel(r'$x$')
plt.ylabel(r'$y$')
plt.title(r'$Sine\ Wave$')
plt.legend([r'${\rm sin}(x)$', r'$0.5\cdot {\rm sin}(x)$'])
plt.show()

運行代碼后效果如下:

美化后的matplotlib

可以看到圖窗中的字體在數學模式下變成了好康的 Computer Modern,最重要的是工具欄也被成功美化。如果對工具欄不滿意的話,可以自己改下 style sheet。以上*( •̀ ω •́ )✧


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM